Frage

Ich arbeite an einer Sammlung von Klassen, die für die Videowiedergabe und -aufzeichnung verwendet werden.Ich habe eine Hauptklasse, die sich wie die öffentliche Schnittstelle verhält, mit Methoden wie play(), stop(), pause(), record() usw...Dann habe ich Arbeitspferdeklassen, die die Videodekodierung und -kodierung übernehmen.

Ich habe gerade von der Existenz verschachtelter Klassen in C++ erfahren und bin neugierig, was Programmierer über deren Verwendung denken.Ich bin etwas vorsichtig und bin mir nicht wirklich sicher, was die Vor- und Nachteile sind, aber sie scheinen (laut dem Buch, das ich lese) in Fällen wie meinem zum Einsatz zu kommen.

Das Buch schlägt vor, dass in einem Szenario wie meinem eine gute Lösung darin bestünde, die Arbeitstierklassen innerhalb der Schnittstellenklasse zu verschachteln, sodass es keine separaten Dateien für Klassen gibt, die der Client nicht verwenden soll, und um mögliche Namenskonflikte zu vermeiden?Ich kenne diese Begründungen nicht.Verschachtelte Klassen sind für mich ein neues Konzept.Ich möchte nur sehen, was Programmierer über das Problem denken.

War es hilfreich?

Lösung

Ich würde hier etwas zögern, verschachtelte Klassen zu verwenden.Was wäre, wenn Sie eine abstrakte Basisklasse für einen „Multimedia-Treiber“ erstellen würden, der die Back-End-Arbeit erledigt (Arbeitstier), und eine separate Klasse für die Front-End-Arbeit?Die Front-End-Klasse könnte einen Zeiger/Referenz auf eine implementierte Treiberklasse (für den entsprechenden Medientyp und die entsprechende Situation) nehmen und die abstrakten Operationen an der Arbeitstierstruktur ausführen.

Meine Philosophie wäre es, dem Kunden beide Strukturen auf ausgefeilte Weise zugänglich zu machen, vorausgesetzt, sie würden gleichzeitig verwendet.

Ich würde auf etwas verweisen wie a QTextDocument in Qt.Sie stellen eine direkte Schnittstelle zur Bare-Metal-Datenverarbeitung bereit, geben die Autorität jedoch an ein Objekt wie QTextEdit weiter, um die Manipulation durchzuführen.

Andere Tipps

Sie würden eine verschachtelte Klasse verwenden, um eine (kleine) Hilfsklasse zu erstellen, die zum Implementieren der Hauptklasse erforderlich ist.Oder zum Beispiel um eine Schnittstelle (eine Klasse mit abstrakten Methoden) zu definieren.

In diesem Fall besteht der Hauptnachteil verschachtelter Klassen darin, dass sie dadurch schwieriger wiederverwendet werden können.Vielleicht möchten Sie Ihre VideoDecoder-Klasse in einem anderen Projekt verwenden.Wenn Sie es zu einer verschachtelten Klasse von VideoPlayer machen, ist dies nicht auf elegante Weise möglich.

Platzieren Sie stattdessen die anderen Klassen in separaten .h/.cpp-Dateien, die Sie dann in Ihrer VideoPlayer-Klasse verwenden können.Der Client von VideoPlayer muss jetzt nur noch die Datei einschließen, die VideoPlayer deklariert, und muss noch nicht wissen, wie Sie sie implementiert haben.

Eine Möglichkeit zu entscheiden, ob verschachtelte Klassen verwendet werden sollen oder nicht, besteht darin, darüber nachzudenken, ob diese Klasse eine unterstützende Rolle oder eine eigene Rolle spielt.

Wenn es nur dazu dient, einer anderen Klasse zu helfen, mache ich es im Allgemeinen zu einer verschachtelten Klasse.Dazu gibt es eine ganze Reihe von Vorbehalten, von denen einige widersprüchlich erscheinen, aber alles hängt von der Erfahrung und dem Bauchgefühl ab.

Klingt nach einem Fall, in dem Sie das verwenden könnten Strategiemuster

Manchmal ist es angebracht, die Implementierungsklassen vor dem Benutzer zu verbergen – in diesen Fällen ist es besser, sie in eine foo_internal.h einzufügen als in die öffentliche Klassendefinition.Auf diese Weise sehen die Leser Ihres foo.h nicht, womit sie Ihrer Meinung nach nicht belästigt werden sollen, aber Sie können dennoch Tests für jede der konkreten Implementierungen Ihrer Schnittstelle schreiben.

Wir sind auf ein Problem mit einem halbveralteten Sun C++-Compiler und der Sichtbarkeit verschachtelter Klassen gestoßen, deren Verhalten sich im Standard geändert hat.Dies ist natürlich kein Grund, Ihre verschachtelte Klasse nicht durchzuführen, sondern nur etwas, das Sie beachten sollten, wenn Sie vorhaben, Ihre Software auf vielen Plattformen, einschließlich alten Compilern, zu kompilieren.

Nun, wenn Sie in Ihrer Interface-Klasse Zeiger auf Ihre Arbeitspferdeklassen verwenden und diese nicht als Parameter oder Rückgabetypen in Ihren Schnittstellenmethoden verfügbar machen, müssen Sie die Definitionen für diese Arbeitspferde nicht in Ihre Schnittstellen-Header-Datei aufnehmen (Sie müssen nur ... vorwärts deklarieren sie stattdessen).Auf diese Weise müssen Benutzer Ihrer Schnittstelle nichts über die Klassen im Hintergrund wissen.

Sie müssen dafür definitiv keine Klassen verschachteln.Tatsächlich machen separate Klassendateien Ihren Code viel lesbarer und einfacher zu verwalten, wenn Ihr Projekt wächst.Es wird Ihnen später auch helfen, wenn Sie eine Unterklasse erstellen müssen (z. B. für verschiedene Inhalts-/Codec-Typen).

Hier finden Sie weitere Informationen zum PIMPL-Muster (Abschnitt 3.1.1).

Sie sollten eine innere Klasse nur verwenden, wenn Sie sie nicht als separate Klasse über die öffentliche Schnittstelle der potenziellen äußeren Klasse implementieren können.Innere Klassen erhöhen die Größe, Komplexität und Verantwortung einer Klasse und sollten daher sparsam eingesetzt werden.

Ihre Encoder-/Decoder-Klasse scheint besser zu passen Strategiemuster

Ein Grund, verschachtelte Klassen zu vermeiden, besteht darin, dass Sie jemals beabsichtigen, den Code mit swig (http://www.swig.org) zur Verwendung mit anderen Sprachen.Swig hat derzeit Probleme mit verschachtelten Klassen, daher wird die Schnittstelle zu Bibliotheken, die verschachtelte Klassen verfügbar machen, zu einem echten Problem.

Beachten Sie außerdem, ob Sie sich jemals unterschiedliche Implementierungen Ihrer Arbeitsfunktionen vorstellen (z. B. Decodierung und Codierung).In diesem Fall möchten Sie auf jeden Fall eine abstrakte Basisklasse mit verschiedenen konkreten Klassen, die die Funktionen implementieren.Es wäre nicht wirklich angebracht, für jeden Implementierungstyp eine eigene Unterklasse zu verschachteln.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top