Warum gibt es in Java keinen Unterklassen-Sichtbarkeitsmodifikator?

Lesezeit: 5 Minuten

Bei mehr als einer Gelegenheit habe ich mir eine variable Sichtbarkeit gewünscht, die in Java nicht möglich ist. Ich wollte, dass bestimmte Mitglieder in ihrer eigenen Klasse und in Unterklassen sichtbar sind, aber nicht für den Rest des Pakets oder den Rest der Welt. Mit anderen Worten, ich wollte Folgendes:

Modifier        Class     Package   Subclass  World
sub-class       Y         N         Y         N

Die Designer von Java gaben mir jedoch nur Dies:

Modifier        Class     Package   Subclass  World
public          Y         Y         Y         Y
protected       Y         Y         Y         N
no modifier     Y         Y         N         N
private         Y         N         N         N

Der typische Fall, in dem ich so etwas möchte, ist das Erstellen einer abstrakten Klasse. Manchmal finde ich, dass der abstrakte Elternteil Zugriff auf bestimmte Mitglieder benötigt, aber konkrete Kinder auch. Ich kann ihnen diesen Zugang geben, indem ich die Mitglieder mache protectedaber das eröffnet den Zugriff auf den Rest des Pakets, wenn ich es nicht wirklich möchte.

Um es ganz klar zu sagen, ich weiß, dass es einen solchen Modifikator gibt nicht in Java möglich. Meine Frage ist, warum ist ein solcher Modifikator nicht in Java enthalten? Es scheint (für mich) ein natürlicheres Sichtbarkeitsniveau zu sein als beides protected oder die Vorgabe. Liegt der Grund nur in der Art, dass es nicht wichtig genug ist, um aufgenommen zu werden, oder hängt es eher mit möglichen Nebenwirkungen zusammen, die ich nicht berücksichtigt habe?

  • Als Problemumgehung für diese Art von Einschränkung könnten Sie die Variablen privat machen und dann eine statische innere Klasse verwenden, um dies zu erreichen.

    – Jeff Foster

    14. März 2011 um 14:49 Uhr

  • Vielleicht, weil die Leute normalerweise Unterklassen erstellen, die in einem anderen Paket als das übergeordnete Paket leben? Ein typisches Beispiel ist das Erweitern von Bibliotheken von Drittanbietern, um unsere eigene Implementierung bereitzustellen.

    – adarshr

    14. März 2011 um 14:50 Uhr

  • @adarshr: Das ist der genaue Grund für die Existenz eines Unterklassenmodifikators. Wenn alle Unterklassen im selben Paket wie die Superklasse wären, wäre es nicht anders als geschützt.

    – aiobe

    14. März 2011 um 14:52 Uhr


  • Zufällig hatte Java 1.0 private protected. Ich glaube, die Implementierung war fehlerhaft. Gefallen am 1.1.

    – Tom Hawtin – Angelleine

    14. März 2011 um 15:03 Uhr

  • Auch ich vermisse diese Sichtbarkeit, aus den gleichen Gründen wie @Michael. Es fühlt sich irgendwie “unnötig” an, meine Klassen in ein separates Paket (abstrakte Oberklasse und konkrete Unterklassen) zu stecken, nur um die Sichtbarkeit einzuschränken. Auch solche hackigen Lösungen wie das Konkretisieren von Superklassen, das Hinzufügen als private Member-Variable in Unterklassen, das Implementieren einer Schnittstelle usw. machen den Code komplizierter, als er sollte. private protected würde die Dinge wirklich schöner machen, indem es die Kapselung beim Erben auf die geringste Komplexität bringt.

    – Robert

    9. September 2014 um 12:27 Uhr


Ich nehme an, sie wollen die zusätzliche Komplexität vermeiden, indem sie eine nichtlineare Zugriffshierarchie haben.

Sie sollten die Kontrolle über Ihr Paket haben, also rufen Sie diese geschützten Methoden dort einfach nicht auf.

(Übrigens, protected ist nicht ganz dasselbe wie sub-class and packageda nicht statische geschützte Methoden (wenn sie nicht im selben Paket enthalten sind) nicht für beliebige Objekte der deklarierenden Klasse aufgerufen werden können, sondern nur für Objekte der Unterklasse, in der sich der Code befindet. (Sie können dies auf sehen Object.clone()die nur von der Klasse aufgerufen werden kann, deren Objekt geklont wird.))

  • Deinen Kommentar in Klammern verstehe ich nicht. geschützt ist Unterklassen-Sichtbarkeit + Paket-Sichtbarkeit. Wie meinst du das?

    – ewernli

    25. April 2013 um 6:34 Uhr

  • @ewernli protected ist etwas weniger. Obwohl jede Klasse von erbt Object (dh clone() sollte überall sichtbar sein), können Sie nicht anrufen anyObject.clone() für ein beliebiges Objekt.

    – Paulo Ebermann

    25. April 2013 um 19:21 Uhr

  • Auf ähnliche Weise kann jede Instanz der Klasse auf die zugreifen private Mitglieder einer anderen Instanz derselben Klasse. Sie würden denken, dass da ein Mitglied ist privatenur diese Instanz sollte darauf zugreifen können, aber wie @PaŭloEbermann sagte, hätten Sie es getan voll Kontrolle über die Klasse bereits. Wenn Sie zugreifen private Mitglieder einer anderen Instanz, es liegt daran Sie habe es so gestaltet. Wenn Sie ein Paket entwickeln und auf a zugreifen protected Mitglied einer anderen Klasse, weil Sie diejenigen sind, die dieses Paket entwickeln, auf das andere keinen Zugriff haben.

    – Michael Plautz

    21. November 2013 um 15:53 ​​Uhr

  • Alte Kommentare / Frage zum Kommentieren, aber kann jemand die Aussage verdeutlichen – “Sie sollten die Kontrolle über Ihr Paket haben”? Wenn ich eine Bibliothek eines Drittanbieters habe, kann ich immer ein Paket mit derselben Hierarchie erstellen und bei Bedarf auf die geschützten Mitglieder zugreifen. Ist das nicht der Fall?

    – Mubin

    22. April 2014 um 14:19 Uhr

  • @Mubin das ist der Fall, ja (wenn es keinen Sicherheitsmanager gibt, der einschränkt, welcher Klassenlader Klassen in einem Paket erstellen kann). Sie könnten aber auch eine modifizierte Version Ihrer Drittanbieterbibliothek erstellen und private Mitglieder öffentlich machen. Oder verwenden Sie Reflexion. Alle diese Zugangsmodifikatoren sind überhaupt nicht wasserdicht.

    – Paulo Ebermann

    22. April 2014 um 18:14 Uhr

Benutzer-Avatar
aiobe

Im selben Paket sein wird einfach als eine engere Beziehung angesehen als ein Untertyp von sein.

Wieso den?

Normalerweise kontrollieren Sie den gesamten Quellcode des Pakets, das Sie entwickeln also hast du wenigstens die Wahrscheinlichkeit

um Fehlanrufe zu vermeiden. Sie machen nicht


steuern Sie den gesamten Code, der Ihre Klassen erweitert. (Jeder kann Ihre Klasse erweitern.) Dies bedeutet, dass der private Zugriff auf Pakete eine wichtigere Rolle spielt. package com.yourpackage; *) Aber hey, ich kann eine beliebige Quelldatei mit starten Sie kontrollieren also nicht den gesamten Code in Ihrem Paket! Nun ja, aber a) sollte man das nicht wirklich tun, und b) kann man es verhindernVerschließen der Pakete

  • . Ich kann mich nicht entscheiden, welche Beziehung meiner Meinung nach enger ist. Mein Instinkt war das ein Untertyp von sein

    war eine engere Beziehung (und vielleicht ist das einer der Gründe, warum ich diese Art von Modifikator für sinnvoller halte als protected und default). Ein beliebiger Programmierer, der eine von mir erstellte JAR-Bibliothek verwendet, könnte jedoch eine meiner Klassen unterteilen, während ich wahrscheinlich weiß, was in meinem Paket vor sich geht. Hmmm…

    – Michael McGowan

  • 14. März 2011 um 15:23 Uhr Ja. Genau denke ich auch. Und du könntest sogar streiken “wahrscheinlich” in Ihrem letzten Satz, wenn Sieversiegeln Sie das Paket

    .

    – aiobe


  • 14. März 2011 um 15:27 Uhr

    Ich habe Schwierigkeiten, mir ein Szenario vorzustellen, in dem Sie kein versiegeltes Paket wünschen würden.

    – corsiKa

13. April 2011 um 22:01 Uhr

1204950cookie-checkWarum gibt es in Java keinen Unterklassen-Sichtbarkeitsmodifikator?

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy