Architektur für Qt SIGNAL mit einem Unterklassen-spezifischen, typisierten Argumenttyp

8

Ich entwickle eine wissenschaftliche Datenerfassungsanwendung mit Qt. Da ich kein Experte für Qt bin, möchte ich von der Community einige Ratschläge zu folgendem Problem erhalten:

Die Anwendung unterstützt mehrere Hardware-Erfassungsschnittstellen, aber ich würde gerne eine gemeinsame API zusätzlich zu diesen Schnittstellen bereitstellen. Jede Schnittstelle hat einen Beispieldatentyp und eine Einheit für ihre Daten. Also repräsentiere ich einen Vektor von Proben von jedem Gerät als std::vector von Boost.Units-Mengen (d. H.% Co_de%). Ich würde gerne eine Multicast-Architektur verwenden, bei der jede Datenquelle neu empfangene Daten an 1 oder mehrere interessierte Parteien sendet. Der Signal / Slot-Mechanismus von Qt passt zu diesem Stil. Daher möchte ich, dass jede Datenquelle ein Signal wie

sendet %Vor%

für die Einheit und den probe_typ, die für dieses Gerät geeignet sind. Da templated std::vector<boost::units::quantity<unit,sample_type> > subclasses vom Metaobjekt-Compiler nicht unterstützt werden, scheint es keine Möglichkeit zu geben, eine (templated) Basisklasse für alle Datenquellen zu haben, die das QObject Signal definiert. Mit anderen Worten, das folgende funktioniert nicht :

%Vor%

Die beste Option, die ich mir ausgedacht habe, ist ein zweischichtiger Ansatz:

%Vor%

Das Signal samplesAcquired gibt jetzt einen Zeitstempel und eine Anzahl von Beispielen für die Erfassung an, und Clients müssen die samplesAcquired API verwenden, um diese Beispiele abzurufen. Natürlich müssen Datenquellen sowohl DataSource als auch IAcquiredSamples ableiten.

Der Nachteil dieses Ansatzes scheint ein Verlust der Einfachheit in der API zu sein ... es wäre viel schöner, wenn Clients die erfassten Samples in den Slot bekommen könnten. Die Möglichkeit, die in der Warteschlange stehenden Verbindungen von Qt zu verwenden, würde auch Threading-Probleme erleichtern, anstatt sie in der Methode IAcquiredSamples innerhalb jeder Unterklasse verwalten zu müssen.

Eine andere Möglichkeit ist die Verwendung eines acquiredData -Arguments. Dies bringt notwendigerweise die Unterklasse dazu, ihren speziellen Abtastvektortyp mit QVariant / Q_REGISTER_METATYPE zu registrieren. Nicht wirklich eine große Sache. Clients der Basisklasse haben jedoch keine Möglichkeit zu wissen, welchen Typ der qRegisterMetaType -Werttyp hat, es sei denn, eine Tag-Struktur wird auch mit dem Signal übergeben. Ich betrachte diese Lösung als mindestens so verschachtelt wie die obige, da sie Clients der abstrakten Basisklassen-API zwingt, sich mit einigen der gröberen Aspekte des Systemtyps zu befassen.

Gibt es also eine Möglichkeit, den templated Signalparameter zu erreichen? Gibt es eine bessere Architektur als die, die ich vorgeschlagen habe?

    
Barry Wark 15.03.2010, 21:58
quelle

4 Antworten

1

Es gibt QVariant-Typ - Sie können Ihren benutzerdefinierten Untertyp darauf erstellen und benutze es als Parameter (wenn ich dein Recht verstehe und das ist, was du willst) in Signalen von Ссылка

    
user204724 16.03.2010 10:40
quelle
1

Eine Vereinfachung Ihres zweischichtigen Ansatzes wäre, die QObject -Klasse als eine nicht-gestützte Basis für die Klassenvorlage, d. h. etwas wie

, zu haben %Vor%

Beachten Sie, dass der Nachteil dieses Ansatzes darin besteht, dass Sie in Qt's Metaobjektsystem keine Informationen darüber finden können, da Sie das Makro Q_OBJECT in der Klassenvorlage nicht verwenden können.

    
Troubadour 31.03.2010 23:41
quelle
1

Qt mag keine Klassenvorlagen, die von QObject erben. Wenn Sie die Laufzeit-Introspektion von QObject nicht benötigen, sollten Sie Boost.Signals verwenden statt dessen, das dieses Problem nicht hat.

Die Einführung der Boost.Signals-Bibliothek in ein Qt-Projekt kann jedoch ein wenig schwierig sein. In Boost.Signals ist signals ein Namespace, während Qt #define s signal bis protected ist. Sie sollten sicherstellen, dass Ihr Qt-Projekt mit QT_NO_KEYWORDS definiert ( CONFIG += no_keywords in qmake) kompiliert, bevor Sie Boost.Signals einführen.

    
Marc Mutz - mmutz 27.04.2011 13:26
quelle
0

Sie können tatsächlich Qt-Klassen mit Templates verwenden, mit kleinen Änderungen an Ihrem Code.

Das Problem mit Qt-Klassen und Templates ist das Moc-Tool, das die Meta-Objektinformationen generiert, es hat überhaupt keine Kenntnisse über Templates, aber der generierte Code muss nicht von Moc kommen.

Sie können Verdigris verwenden, um Ihre C ++ / QObject-Klasse zu erstellen, die wird Arbeiten Sie mit Vorlagen ohne Probleme und umgehen Sie den Moc-Schritt für solchen Code.

    
Tomaz Canabrava 05.04.2017 15:29
quelle

Tags und Links