Qt, MOC: 'QObject' is an ambiguous base of 'MainWindow'

OP #3968271
Hallo,

ich experimentiere mit einer Qt-Bedienoberfläche (MainWindow) als 
Basisklasse von der mehrere Klassen mit unterschiedlichen 
Funktionaltäten ableitet werden sollen.

Betriebssystem Ubuntu 14.04
Compiler GCC x86,32 bit
Qt 5.3.0 GCC 32bit

Fehlermeldungen:
1
moc_mainwindow.cpp: In member function 'virtual const QMetaObject* MainWindow::metaObject() const':
2
moc_mainwindow.cpp:141:21: error: 'QObject' is an ambiguous base of 'MainWindow'
3
     return QObject::d_ptr->metaObject ? QObject::d_ptr->dynamicMetaObject() : &staticMetaObject;
4
                     ^
5
moc_mainwindow.cpp:141:50: error: 'QObject' is an ambiguous base of 'MainWindow'
6
     return QObject::d_ptr->metaObject ? QObject::d_ptr->dynamicMetaObject() : &staticMetaObject;
7
                                                  ^
8
moc_mainwindow.cpp:142:1: warning: control reaches end of non-void function [-Wreturn-type]
9
 }
10
 ^
11
make: *** [moc_mainwindow.o] Error 1
12
16:51:30: Der Prozess "/usr/bin/make" wurde mit dem Rückgabewert 2 beendet.
13
Fehler beim Erstellen/Deployment des Projekts Stellwerk1_3 (Kit: Desktop Qt 5.3.0 GCC 32bit)
14
Bei der Ausführung von Schritt 'Make'
15
16:51:30: Verstrichene Zeit: 00:01.
Weiß jemand, woran das liegt?


-------------------------    Anhang    ----------------------

mainwindow.hpp:
1
#include <QMainWindow>
2
#include <QObject>
3
#include <ftdi.hpp>
4

5
namespace Ui {
6
class MainWindow;
7
}
8
using namespace Ftdi;
9

10
class abBus : QObject, public Context, public List{
11

12
    Q_OBJECT
13

14
public:
15
    int vid;
16
    int pid;
17
    int baudrate;
18
    int index;
19
    int empfangen;
20

21
    int ret_flowctrl;
22

23
public:
24
    abBus();
25
    ~abBus();
26

27
};
28

29
class MainWindow : public abBus, public QMainWindow
30
{
31
    Q_OBJECT
32

33
public:
34
    explicit MainWindow(QWidget *parent = 0);
35
    ~MainWindow();
36

37

38
private:
39
  Ui::MainWindow *ui;
40
};

mainwindow.cpp:
1
#include "mainwindow.h"
2
#include "ui_mainwindow.h"
3

4
#include <stdio.h>
5
#include <iostream>    // Streams cin, cout, cerr, clog
6
#include <iomanip>     // Manipulatoren zur Formatierung der Ausgabe
7
#include <cstdlib>     // definiert die Makros, die traditionsgemäß in der <stdlib.h> definiert sind
8
#include <cstring>     // Microsoft-spezifische Zeichenfolgenklassen
9

10

11
using namespace Ftdi;
12

13
MainWindow::MainWindow(QWidget *parent) :
14
    QMainWindow(parent),
15
    ui(new Ui::MainWindow)
16
{
17
    ui->setupUi(this);
18
    empfangen=1;
19

20
    abBus* rail=new abBus;
21

22
    // Datenflusssteuerung durch RFR/CTS
23

24
    printf("\nDatenflußsteuerung RTS_CTS einschalten: ");
25
    rail->ret_flowctrl=set_flow_control(SIO_RTS_CTS_HS);
26
    if (ret_flowctrl < 0) {
27
        switch(ret_flowctrl){
28
            case -1:
29
                printf("Flusskontrolle gescheitert");
30
                break;
31

32
            case -2:
33
                printf("USB-Gerät nicht verfügbar");
34
                break;
35
        }
36
    } else printf("Datenflußsteuerung RTS_CTS, i.O.");
37

38
}
39

40
MainWindow::~MainWindow()
41
{
42
    delete ui;
43
}

main.cpp
1
#include "mainwindow.h"
2
#include <QApplication>
3

4
int main(int argc, char *argv[])
5
{
6
    QApplication a(argc, argv);
7
    MainWindow w;
8
    w.show();
9

10
    return a.exec();
11
}
#3968284
Das geht nicht. Jedes Objekt kann nur eine Basisklasse haben, die ein 
QObject ist. Ich hab deinen Code nicht gelesen und weiß deshalb nicht 
was du erreichen willst, wenn du das mal erklärst, findet sich bestimmt 
eine bessere Lösung.
#3968298
Aribert Börner schrieb:


> class abBus : QObject, public Context, public List{
>
>     Q_OBJECT
>
> public:
>     int vid;
>     int pid;
>     int baudrate;
>     int index;
>     int empfangen;
>
>     int ret_flowctrl;
>
> public:
>     abBus();
>     ~abBus();
>
> };

offenbar irgend eine Bussteuerung

> class MainWindow : public abBus, public QMainWindow

Das ist unlogisch.

Ein Mainwindow ist ein Grafikelement. Ein Fenster, das etwas anzeigt.
Aber ein derartiges Fenster ist KEINE Bussteuerung.

Innerhalb des Main WIndows existiert vielleicht eine Bussteuerung. Die 
Bussteuerung ist innerer Bestandteil dieses Fensters. Aber ein Fenster 
IST KEINE Bussteuerung.

Das ist so wie ein Auto einen Motor HAT. Aber ein Auto IST KEIN Motor!

Deine Klassenhierarchieen werden wesentlich besser, wenn du dich an eine 
relativ einfache Daumenregel hältst:

Besteht zwischen 2 Klassen eine "IST-EIN" Beziehung, dann willst du eine 
Klasse von der anderen ableiten.

Besteht aber zwischen den beiden Klassen eine "HAT-EIN" Beziehung, dann 
bedeutet das, dass es einen entsprechenden Daten-member gibt.

Ein Auto IST EIN Kraftfahrzeug
1
class Kraftfahrzeug
2
{
3
  ...
4
};
5

6
class Auto : public Kraftfahrzeug
7
{
8
  ...
9
};

Aber:
Ein Kraftfahrzeug HAT EINEN Motor
1
class Motor
2
{
3
  ...
4
};
5

6
class Kraftfahrzeug
7
{
8
  ...
9
protected:
10
  Motor  motor_;
11
};


und um Mehrfach-Ableitung solltest du sowieso einen Bogen machen. Die 
wirft mehr Probleme auf, als sie meistens löst. Wenn man mehrfach 
ableitet, dann eher im Sinne von Interfaces, so wie das Java 
vorexerziert.
OP #3968386
hallo,
habe jetzt in der Klasse abBus das QObject herausgenommen.

Resultat:
1
g++ -c -pipe -g -Wall -W -D_REENTRANT -fPIE -DQT_WIDGETS_LIB -DQT_GUI_LIB -DQT_CORE_LIB -I../../Qt5.3.0/5.3/gcc/mkspecs/linux-g++ -I../Stellwerk1_3 -I../../Qt5.3.0/5.3/gcc/include -I../../Qt5.3.0/5.3/gcc/include/QtWidgets -I../../Qt5.3.0/5.3/gcc/include/QtGui -I../../Qt5.3.0/5.3/gcc/include/QtCore -I. -I. -I. -o moc_mainwindow.o moc_mainwindow.cpp
2
moc_mainwindow.cpp:63:8: error: 'staticMetaObject' is not a member of 'abBus'
3
     { &abBus::staticMetaObject, qt_meta_stringdata_MainWindow.data,
4
        ^
5
moc_mainwindow.cpp: In member function 'virtual void* MainWindow::qt_metacast(const char*)':
6
moc_mainwindow.cpp:80:12: error: 'qt_metacast' is not a member of 'abBus'
7
     return abBus::qt_metacast(_clname);
8
            ^
9
moc_mainwindow.cpp: In member function 'virtual int MainWindow::qt_metacall(QMetaObject::Call, int, void**)':
10
moc_mainwindow.cpp:85:11: error: 'qt_metacall' is not a member of 'abBus'
11
     _id = abBus::qt_metacall(_c, _id, _a);
12
           ^
13
moc_mainwindow.cpp: In member function 'virtual void* MainWindow::qt_metacast(const char*)':
14
moc_mainwindow.cpp:81:1: warning: control reaches end of non-void function [-Wreturn-type]
15
 }
16
 ^
17
make: *** [moc_mainwindow.o] Error 1
18
18:37:04: Der Prozess "/usr/bin/make" wurde mit dem Rückgabewert 2 beendet.
19
Fehler beim Erstellen/Deployment des Projekts Stellwerk1_3 (Kit: Desktop Qt 5.3.0 GCC 32bit)
20
Bei der Ausführung von Schritt 'Make'
was wäre jetzt angebracht ?
Gast #3968430
Was mächtest Du eigentlich erreichen? Bis jetzt hast Du ein Fentser 
(QMainWindow) und sonst weiter nichts... wenn Du eine Konsolenanwendung 
schreiben willst, dann nutze die QCoreApplication Klasse....

Btw... hast Du schon mal mit C++/Qt und einer objektorientierter Sprache 
zu tun gehabt?
Gast #3969624
make clean.

"public abBus" Vererbung in Mainwindow raus.

Generell: Finger weg von Mehrfachvererbung solange du das entsprechende 
Kapitel in deinem C++-Buch nicht gelesen hast.

Antwort schreiben

Eine eigene Frage? Dieser Thread ist über 11 Jahre alt. Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.

Neuen Thread starten

Eine Lösung, Ergänzung oder Rückmeldung zu diesem Thread? Dann antworte hier.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.