Autor Beitrag
_mk_
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 23



BeitragVerfasst: Di 16.08.22 14:14 
Hallo Zusammen.

Da ich nur über ein Paar C#-Grundlage verfüge, weiß ich (noch) nicht wie ich diese Compilerfehlermeldung "Inkonsistenter Zugriff: Eigenschaftentyp "Countries" ist weniger zugreifbar als Eigenschaft "Person.Country"." beheben könnte. Die Enumeration möchte ich keineswegs öffentlich deklarieren. Ich habe leider keinen Ansatz, wie es lösen kann, noch habe ich keine Ahnung, wonach ich hier im Internet suchen sollte. Die Links zu CS0051 und CS0053 helfen mir leider nicht weiter.

Vielen Dank im Voraus.


TempLib_-_Microsoft_Visual_Studio
Einloggen, um Attachments anzusehen!
Palladin007
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 1282
Erhaltene Danke: 182

Windows 11 x64 Pro
C# (Visual Studio Preview)
BeitragVerfasst: Di 16.08.22 14:20 
Das geht nicht.

Du hast dem Enum keinen Zugriffsmodifizierer gegeben, damit greift der Default internal.
Deine Person-Klasse ist aber public, wodurch sie auch das Enum public macht, ansonsten kann man die Person-Klasse nicht nutzen.
Das sagt der Fehler aus.

Lösen kannst Du das nur, indem Du das enum auch public oder die betroffenen Inhalte der Person-Klasse internal machst, doch dann kann man sie nicht mehr public nutzen.

Aber was verstehst Du denn eigentlich unter internal und public?
Lies das mal nach, eventuell hast Du ja etwas falsch verstanden: Access Modifiers

Moderiert von user profile iconTh69: URl-Titel hinzugefügt

Für diesen Beitrag haben gedankt: _mk_
_mk_ Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 23



BeitragVerfasst: Di 16.08.22 14:38 
user profile iconPalladin007 hat folgendes geschrieben Zum zitierten Posting springen:
Aber was verstehst Du denn eigentlich unter internal und public?
Lies das mal nach, eventuell hast Du ja etwas falsch verstanden: Access Modifiers

Dann habe ich es in der Tat falsch verstanden. Unter den Modifizierer public verstehe ich, dass die Klasse auch außerhalb des Assemblies instanziiert werden kann und unter internal vertehe ich, dass auf die Klasse nur innerhalb des Assemblies zugegriffen werden kann. Wenn ich das Projekt kompliere, befinden sich doch alle Klassen und Stukturen in einem Assembly? Wo ist hier mein Denkfehler?

Vielen Dank im Voraus.
Th69
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Moderator
Beiträge: 4764
Erhaltene Danke: 1052

Win10
C#, C++ (VS 2017/19/22)
BeitragVerfasst: Di 16.08.22 15:06 
Wenn du eine Eigenschaft oder Methode als public deklarierst, so muß auch der Rückgabetyp public sein, sonst könnte der Aufrufer (aus einer anderen Assembly) ja gar nicht diesen Datentyp verwenden.

Edit: Die Schweiz schreibt sich im englischen auch leicht anders...

Für diesen Beitrag haben gedankt: _mk_
Palladin007
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 1282
Erhaltene Danke: 182

Windows 11 x64 Pro
C# (Visual Studio Preview)
BeitragVerfasst: Di 16.08.22 15:21 
Zitat:
Unter den Modifizierer public verstehe ich, dass die Klasse auch außerhalb des Assemblies instanziiert werden kann und unter internal vertehe ich, dass auf die Klasse nur innerhalb des Assemblies zugegriffen werden kann.

Das ist korrekt.

Zitat:
Wenn ich das Projekt kompliere, befinden sich doch alle Klassen und Stukturen in einem Assembly? Wo ist hier mein Denkfehler?

Der Denkfehler ist, so meine Vermutung, dass es hier nicht um die Assembly geht, an der Du gerade arbeitest, sondern *andere* Assemblies, die deine Assembly nutzen wollen.
Das public sagt aus, dass *andere* Assembly die Person-Klasse nutzen und den Konstruktor aufrufen können, das internal verbietet das. Innerhalb deiner Assembly ist das egal, da kann man beides gleichermaßen nutzen.

Angenommen, deine Assembly liefert ein paar Tools für einen anderen Entwickler.
In dem Fall hast Du natürlich Klassen, Methoden, etc., die andere Entwickler nutzen wollen und das muss alles public sein.
Allerdings hast Du auch Dinge, die nur für dich und deine Implementierung wichtig sind, die anderen Entwickler dürfen sie nicht nutzen, um nichts kaputt machen zu können. Das sollte in der Regel internal sein.

Oder Du bist eine Firma, die Produkte verkauft und dafür Maschinen braucht.
Der Kunde ist nicht Teil der Firma, darf aber die Produkte kaufen und verwenden => public
Die Maschinen dürfen aber nur von Mitarbeitern der Firma verwendet werden => internal

Wenn es aber keine anderen Assemblies gibt, die dein Projekt nutzen sollen, dann ist das für dich ziemlich irrelevant.
Du kannst also getrost alles public oder internal machen, das ist dann eine Frage des Stils - solange die Regel, über die Du hier gestolpert bist, erfüllt wird.
Ich persönlich bevorzuge internal.

Für diesen Beitrag haben gedankt: _mk_
_mk_ Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 23



BeitragVerfasst: Di 16.08.22 16:10 
user profile iconTh69 hat folgendes geschrieben Zum zitierten Posting springen:
Wenn du eine Eigenschaft oder Methode als public deklarierst, so muß auch der Rückgabetyp public sein, sonst könnte der Aufrufer (aus einer anderen Assembly) ja gar nicht diesen Datentyp verwenden.

Langsam kommt Licht im Dunkeln. Ich war der Meinung, dass es völlig ausreichend ist, wenn in diesem Beispiel die Klasse Person die Enumeration Countries sieht und die Klasse weiß, woher er seine Informationen bekommt und diese bereitstellt. Deshalb wollte ich den standardmäßiger Zugriffsmodifzierer verwenden. Mir war nicht klar, dass quasie der gesamte Datentyp weitergereicht wird und deshalb der Aufrufer auch Kenntnis über den Datentyp benötigt. Vielleicht denke ich noch nicht objektorientiert genug.

Ich habe da noch ein ganz viel zu lernen.

user profile iconTh69 hat folgendes geschrieben Zum zitierten Posting springen:
Edit: Die Schweiz schreibt sich im englischen auch leicht anders...

Danke für den Hinweis. Wobei es sich eigentlich nur um kleines Beispiel handelte. Switzerland soll es natürlich heißen.
_mk_ Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 23



BeitragVerfasst: Mi 17.08.22 10:55 
user profile iconPalladin007 hat folgendes geschrieben Zum zitierten Posting springen:
Angenommen, deine Assembly liefert ein paar Tools für einen anderen Entwickler.
In dem Fall hast Du natürlich Klassen, Methoden, etc., die andere Entwickler nutzen wollen und das muss alles public sein.
Allerdings hast Du auch Dinge, die nur für dich und deine Implementierung wichtig sind, die anderen Entwickler dürfen sie nicht nutzen, um nichts kaputt machen zu können. Das sollte in der Regel internal sein.

Oder Du bist eine Firma, die Produkte verkauft und dafür Maschinen braucht.
Der Kunde ist nicht Teil der Firma, darf aber die Produkte kaufen und verwenden => public
Die Maschinen dürfen aber nur von Mitarbeitern der Firma verwendet werden => internal

Vielen Dank für Deine Ausführung und für Dein Beispiel.

Ich tue mich aber noch etwas schwer damit. Aber ich denke, das sollte aber für den Anfang reichen.
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4700
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Mi 17.08.22 16:24 
Vielleicht kurz aus einer anderen Richtung.
Es wäre ein Kompiler denkbar der deinen Code zuläßt aber was würde das aber bedeuten?

Der Konstruktor ist public. Könntest du dann im public Scope eine Person erzeugen? Nein denn ein new Person(Countries.Austria) geht nicht da du Countries nicht benutzen darfst es ist internal.

Bei der Property stellen wir uns vor du hättest von irgendwoher im public scope eine Instanz von Person an der Hand. Könntest du irgendwas mit der Property anfangen. Du könntest ein meineLiebePersonInstanz.Country; aufrufen. Wenn du den returnten enum ignorierst. Macht das Sinn? Nein. Könntest du irgendwas sinnvolles machen? Z.B. den Wert prüfen via if (meineLiebePersonInstanz.Country == Countries.Austria). Nö wieder das Problem das du Countries nicht benutzen darfst.

Ergo du könntest niemals den Person Typ außerhalb des internal scope benutzen selbst wenn dein Code zulässig wäre. Ergo ist der Error den der Compiler liefert eigentlich eher ein Service der dir sagt es ist sinnlos die Klasse public zu machen. Er meldet es halt nicht nur sondern erfordert es auch hart.

Für diesen Beitrag haben gedankt: _mk_
_mk_ Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 23



BeitragVerfasst: Do 18.08.22 14:24 
Vielen Dank für Deine Erklärung, user profile iconRalf Jansen. Es wird jetzt immer deutlicher, warum und wie ich die Zugriffsmodifierer einzusetzen habe. Leider wird dieses Thema in den Büchern, die ich zu C# lese, nur sehr kurz behandelt.

OOP ist noch sehr abstrakt für mich. Daran gewöhne ich mich erst langsam.