Werden Verschachtelungstypen als schlechte Praxis angesehen?

8

Werden Verschachtelungstypen (z. B. aufgezählte Typen oder Strukturen in einer Klasse), wie im Titel erwähnt, als schlechte Praxis angesehen oder nicht? Wenn Sie Code Analysis in Visual Studio ausführen, wird die folgende Meldung zurückgegeben, die impliziert, dass dies der Fall ist:

Warnung 34 CA1034: Microsoft.Design: Verschachteln Sie den Typ 'ClassName.StructueName' nicht. Alternativ können Sie die Zugänglichkeit so ändern, dass sie von außen nicht sichtbar ist.

Wenn ich jedoch der Empfehlung der Codeanalyse folge, stelle ich fest, dass in der Anwendung häufig viele Strukturen und Aufzählungstypen herumschwirren, die möglicherweise nur für eine einzelne Klasse gelten oder nur für diese Klasse verwendet werden. Wäre es als solches angemessen, den Typ Sünde in diesem Fall zu verschachteln, oder gibt es einen besseren Weg, dies zu tun?

rjzii
quelle
Diese Frage ist SEHR eng mit programmers.stackexchange.com/questions/34067 verbunden. Ich bin hin und her gerissen, ob ich diese als Duplikat schließen soll ...
Walter
@Walter - Sie sind nah beieinander, aber ich habe die Frage gehört, die separat gestellt wurde, um Klassen in Klassen zu verschachteln und alle anderen Typen in Klassen separat zu verschachteln, damit es nicht schaden kann. Wie sich herausstellte, habe ich diese Frage bei meiner ursprünglichen Suche nicht gefunden.
rjzii

Antworten:

15

Verschachtelte Typen sind nicht schlecht. Die Warnung, die Sie erhalten, bedeutet nicht, dass Sie niemals einen verschachtelten Typ haben. Es zeigt lediglich an, dass Ihr verschachtelter Typ einen geeigneten Zugriffsmodifikator und Code-Speicherort verwenden sollte.

Wenn der verschachtelte Typ wirklich nur innerhalb der enthaltenden Klasse verwendet wird (dh es handelt sich um einen internen Datencontainer oder eine Statusanzeige), setzen Sie den Zugriffsmodifikator auf privat.

Wenn der verschachtelte Typ Teil einer oder mehrerer Methodensignaturen ist, ist er tatsächlich nicht lokal für die enthaltende Klasse. Es stellt eine Nachricht dar, die an oder von Instanzen der enthaltenden Klasse übergeben wird. In diesem Fall ist es wahrscheinlich besser, den verschachtelten Typ aus der enthaltenen Klasse zu verschieben und ihm einen Open-Access-Modifikator wie "intern" oder "öffentlich" zuzuweisen.

Kurz gesagt, die Warnung scheint zu empfehlen, lokale Typen privat zu machen, und freigegebene Typen sollten eigenständig sein.

JeremyDWill
quelle
Der interne Modifikator ist das, was ich in den meisten Fällen getan habe. Er räumt ein bisschen auf, aber es schweben viele davon in der Anwendung herum.
rjzii
1

Wenn es nur von dieser Klasse verwendet wird, sollte es privat gemacht werden, und genau das schlägt die Nachricht vor.

Otávio Décio
quelle
In einigen Fällen wird dies durchgeführt, in anderen Fällen wird in Methodenaufrufen, die an die Klasse angehängt sind, ein Aufzählungstyp verwendet. Ebenso habe ich auch Strukturen gesehen, die für Methodenklassen verwendet werden, wenn die Anzahl der Parameter eine bestimmte Anzahl überschreitet.
rjzii
0

Die Warnung zu Verschachtelungstypen war einer der ersten "Vorschläge", die ich vor einiger Zeit erhalten habe, nachdem ich die Codeanalyse aktiviert hatte. Es war auch der Grund, warum ich es ausgeschaltet habe.

Einige Vorschläge sind wirklich fremd, als ob sie von einem anderen Planeten stammen.

Ich füge Aufzählungen in Klassen ein, um die Dinge logisch zusammenzuhalten.

Stellen Sie sich das so vor: Wenn Verschachtelungstypen in allen Fällen absolut böse gewesen wären, warum hätten die Sprachdesigner sie überhaupt implementiert? Weil es in vielen Fällen nützlich ist und in dieser Hinsicht die Warnung lediglich darauf hinweist, dass etwas in Ihrem Code möglicherweise nicht optimal ist. Ob dies zutrifft oder nicht, liegt bei Ihnen.


quelle
2
Ein Namespace sollte Ihre logische Gruppierung für die Aufzählung sein. nicht die Klasse
Aaron McIver
1
Nun, in einigen Situationen finde ich es unpraktisch.
Wenn Sie die Enumeration derzeit in der Klasse platzieren und sie außerhalb der Klasse verschieben, sodass sie sich im Namespace befindet, wird STRG + X in Verbindung mit STRG + V benötigt. Sie sind sich nicht sicher, wie dies unpraktisch werden würde?
Aaron McIver
Ich stelle manchmal meine Aufzählungen in Klassen. Ich denke, es gibt legitime Gründe dafür - es ist keine strenge Regel.
Niemand
3
@rmx Ich habe noch nie eine Aufzählung innerhalb einer einzelnen Klasse verwendet. Es wird immer in mehreren Klassen verwendet, daher ist es viel sinnvoller, es im Namespace als eigene Entität zu definieren.
Aaron McIver
0

Nein

Ein gutes Beispiel in C # ist IEnumerable, bei dem andere Klassen nicht die genaue zurückgegebene Klasse kennen müssen, sondern nur, dass es sich um einen IEnumerator handelt. Daher ist es sinnvoll, es zu einer verschachtelten Klasse zu machen, da sonst möglicherweise viele kleine Klassen in Intellisense herumschweben, das IEnumerator implementiert

Homde
quelle
In einigen Fällen kann die Laufzeiteffizienz verbessert werden, wenn ein Compiler den von zurückgegebenen Typ kennt GetEnumerator(). aus diesem Grund List<T>.GetEnumerator()zurück List<T>.Enumerator(). Wenn es eine Möglichkeit gewesen wäre, den Compiler zu bitten, eine andere benannte Methode zu verwenden, wäre es möglicherweise besser gewesen, diese Methode zu haben, z. B. ForEachGetEnumerator()return List<T>.Enumeratorund GetEnumerator()return IEnumerator<T>, aber dafür gibt es keinen Mechanismus.
Supercat