2013-12-07 3 views
-1

Я определил свой собственный класс в проекте Qt, который дает мне проблемы, но я думаю, что это может быть общий C++.Проблемы с указателем на класс

Когда я пытаюсь объявить указатель на мой класс в любой включаемый файл в проекте myHashMap как

myHashMap* map; 

компилятор выдает ошибку и сказать: «множественное определение карты». Что это? Я даже не определил указатель, даже объявил его.

Однако размещение myHashMap* map в исходном файле не дает никаких ошибок.

Вот определение и объявление класса, извините, что это выглядит немного грязно.

#include QObject 
#include QHash 

class myHashMap : public QObject 
{ 
    Q_OBJECT 
public: 
    explicit myHashMap(QObject *parent = 0); 

    float Get(const QString& key) const; 

    void setValue(const char key, float value) 
    { 
     // only emit value changed if the value has actually changed 

     //if(hash->value(key) != value) 
     //{ 
       hash->insert(key,value); 
       //emit ValueChanged(key, value); 
     //} 
    } 

signals: 

public slots: 
    //void ValueChanged(const char& key, float newValue); 

private: 
    QHash<const char, float>* hash; 
}; 

myHashMap::myHashMap(QObject *parent) : 
    QObject(parent) 
{ 
    hash = new QHash<const char,float>; 
} 

EDIT:

Ааа, облом, я просто забыл предварять MyHashMap * с экстерном ключевого слова. Программирование C++ - это ничтожно. Разве это не имеет смысла, если компилятор отправил предупреждение здесь, например, «привет, теперь у вас есть несколько определений в нескольких заголовках, забыли ключевое слово extern?» ?

Однако у меня возникла новая проблема.

В «communication.h» Я предрек пространство имен, как этот

namespace reference 
{ 
    extern const char potentiometer; 
    extern const char KpAngle; 
    extern const char KiAngle; 
    extern const char KdAngle; 

    extern const int  length; 

    extern myHashMap* hmap; 

    void init(); 
} 

В communication.cpp я хочу использовать * HMAP, как показано ниже, но компилятор возвращает «неопределенная ссылка на HMAP». Тем не менее, я включил «communication.h» как в «communication.cpp», так и в файл * .pro. См. Код ниже:

#include "communication.h" 
    namespace reference 
    { 
    const char potentiometer  = 0x05; 
    const char KpAngle   = 0x06; 
    const char KiAngle   = 0x07; 
    const char KdAngle   = 0x08; 

    const int length   =1; 

    //QList<const char>* summary = new QList<const char>(); 

    void init() 
    { 
      //using namespace reference; 
      //#include "communication.h" 
     //myHashMap* hmap = new myHashMap(); 
     //when using this a hmap is created, however setValue returns undefined ref    
     //Both methods below returns "undefine reference to hmap". Same if i try "using namespace" 
      //reference::hmap = new myHashMap(); 
      //hmap = new myHashMap(); 


      /* 
      reference::hmap->setValue(potentiometer,-1); 
      reference::hmap->setValue(KpAngle,-1); 
      reference::hmap->setValue(KiAngle,-1); 
      reference::hmap->setValue(KdAngle,-1);*/ 
    } 


} 

EDIT: Над указателем hmap указано только, не определено. Поэтому я определил hmap, установив

myHashMap * hmap непосредственно в справочной области в «communication.cpp». Теперь это работает.

+0

Попробуйте переименовать карту на что-то еще, например myMap. –

+0

Ваша первая строка недействительна C++; опубликуйте свой реальный код. Какие еще определения «map» компилятор упоминает? –

+0

Комментарий к вашей второй проблеме: включили ли вы заголовочный файл для myHashMap в comunications.h? –

ответ

-1

Скорее всего, имя «карта» уже зарезервировано другой переменной или функцией в используемой вами библиотеке. Также если вы включаете заголовок в другие заголовки, все из которых включены в ваш основной файл, вы можете получить эту ошибку ,

+0

Я пробовал переименовать «карту» без результата. Заголовок «myhashmap.h» не включен в другие заголовки так, как вы описываете. – user3050215

0

Префикс объявления extern в файле заголовка; т.е .:

extern myHashMap* map; 

Вам также необходимо поместить определение переменной (без extern) в исходный файл где-нибудь.

Причина, по которой возникает проблема, заключается в том, что заголовочные файлы обычно включаются в несколько исходных файлов. Каждый исходный файл скомпилирован в своей собственной единицы перевода независимо от всех остальных. Если вы поместите объявление переменной в заголовочный файл, вы получите несколько единиц перевода, которые пытаются определить одну и ту же переменную, вызывая конфликт.

Вы хотите, чтобы переменная существовала только внутри единой единицы перевода, поэтому объявление в одном исходном файле. Версия extern просто указывает, что существует (или будет) переменная с этим именем и типом, но на самом деле она не может быть создана. Это эффективно делает его видимым для всего, что его видит.

+0

Этот ответ прямо на. C++ - мелочный, не так ли? Однако аккуратность Qt немного компенсирует это. Есть ли Qt-программа, в которой, например, есть Java или Python? – user3050215

+0

Многие причуды C++ существуют по причинам, связанным с наследием, или потому, что для них все еще есть случайное использование. Я не склонен использовать Java или Python, поэтому, боюсь, я не знаю о эквиваленте Qt. –

Смежные вопросы