2014-12-21 3 views
0

Моя типовая программа настолько мала, что я собираюсь дать вам весь исходный код ниже:Малый типовая программа дает мне ошибку

Так вот ClassA Заголовок:

#ifndef CLASSA_H 
#define CLASSA_H 
#include <string> 

class ClassA 
{ 
public: 
    ClassA(const std::string& fileName, int TYPE = 0, float filter = 0.0f); 
    ClassA(int width = 0, int height = 0, unsigned char* data = 0, int TYPE = 0, float filter = 0.0f); 
    ClassA(ClassA& classa); 
    void operator=(ClassA& classa); 
protected: 

private: 
    std::string m_lastBind; 
    int m_textureTarget; 
    bool m_freeTexture; 
    int m_width; 
    int m_height; 
    float m_float; 

}; 

#endif // CLASSA_H 

Вот источник файл для ClassA:

#include "classa.h" 

ClassA::ClassA(const std::string& fileName, int TYPE, float filter) 
{ 
    m_lastBind = fileName; 
    m_textureTarget = TYPE; 
    m_float = filter; 
} 


static unsigned char whitePixel[] = {'A', 'B', 'B', 'A'}; 

ClassA::ClassA(int width, int height, unsigned char* data, int TYPE, float filter) 
{ 
    m_width = width; 
    m_height = height; 
    data = whitePixel; 
    m_textureTarget = TYPE; 
    m_float = filter; 
} 


ClassA::ClassA(ClassA& classa) 
{ 
    m_width = classa.m_width; 
    m_height = classa.m_height; 
    m_textureTarget = classa.m_textureTarget; 
    m_float = classa.m_float; 
} 

Вот файл заголовка для ClassB:

#ifndef CLASSB_H 
#define CLASSB_H 
#include <string> 

class ClassB 
{ 
    public: 
     void someMethod(const int& num1, const int& num2, std::string& name); 
    protected: 

    private: 
}; 

#endif // CLASSB_H 

И, наконец, определение одного и единственного метода ClassB приведен ниже:

#include "classb.h" 
#include "classa.h" 

static unsigned char whitePixel[] = {0xFF, 0xFF, 0xFF, 0xFF}; 
void ClassB::someMethod(const int& num1, const int& num2, std::string& name) 
{ 
    static ClassA WHITE = ClassA(1,1,whitePixel); 
} 

Основная функция в значительной степени не имеет значения, потому что она совершенно пуста и не имеет ничего общего с ошибками я получаю от Code :: Blocks. Ошибки приведены ниже:

||=== Build: Debug in Testing2 (compiler: GNU GCC Compiler) ===| 
classb.cpp||In member function ‘void ClassB::someMethod(const int&, const int&, std::string&)’:| 
classb.cpp|8|error: no matching function for call to ‘ClassA::ClassA(ClassA)’| 
classb.cpp|8|note: candidates are:| 
classa.h|10|note: ClassA::ClassA(ClassA&)| 
classa.h|10|note: no known conversion for argument 1 from ‘ClassA’ to ‘ClassA&’| 
classa.h|9|note: ClassA::ClassA(int, int, unsigned char*, int, float)| 
classa.h|9|note: no known conversion for argument 1 from ‘ClassA’ to ‘int’| 
classa.h|8|note: ClassA::ClassA(const string&, int, float)| 
classa.h|8|note: no known conversion for argument 1 from ‘ClassA’ to ‘const string& {aka const std::basic_string<char>&}’| 
||=== Build failed: 1 error(s), 0 warning(s) (0 minute(s), 0 second(s)) ===| 
+0

Второе, что я думаю. –

+0

Ваш компилятор не знает тип параметров (например, int или reference). Вы должны наложить 1-й параметр (возможно, 2-й параметр) на int. –

+0

@VuDang: нет! Компилятор знает типы. – Mat

ответ

4

Эта линия:

static ClassA WHITE = ClassA(1,1,whitePixel); 

нужна копия-конструктор для работы. Конструктор ClassA(ClassA&) не будет соответствовать, потому что временные файлы не могут связываться с lvalue-ссылками. Вы можете сделать конструктор вместо ссылки на const.

ClassA(ClassA const&); 

Это работает, потому что (rvalues ​​временных) может связываться с Lvalue ссылки на const.


Что вы делали, создавая временную ClassA ценность и копирования построенияWHITE от этого. Это называется копирование-инициализация. Если вы используете прямую инициализацию вместо:

static ClassA WHITE(1,1,whitePixel); 

Копия-конструктор просто копирует все член параметра к создаваемому объекту. Ваш код эффективно делает то же самое. К счастью, компилятор предоставит вам конструктор-копию по умолчанию, так что вам не нужно делать самостоятельно.

+0

Почему компилятор интерпретирует вызов конструктора с тремя аргументами в качестве вызова конструктора копирования? –

+0

Кроме того, хороший аватар. –

+0

@KyleStrand Во время разрешения перегрузки компилятор собирает кандидатов для вызова. Когда он терпит неудачу, он перечисляет кандидатов и почему они не являются жизнеспособными. Мой ответ идет по тому, что, по моему мнению, он был конструктором-копиром. – 0x499602D2

3
static ClassA WHITE = ClassA(1,1,whitePixel); 

Это создает временный ClassA, а затем скопировать конструирует WHITE из него. Копия может быть удалена путем оптимизации, но она может быть должна быть.

Вы должны просто прямо заявить WHITE:

static ClassA WHITE(1, 1, whitePixel); 
+0

Ohhhhhhhh. Правильно. –

1
static ClassA WHITE = ClassA(1,1,whitePixel); 

Это копия инициализация, которая семантически первый создает правую часть, а затем инициализирует левую часть, вызвав конструктор копирования (этот вызов может быть eled, но конструктор копирования должен быть доступен).Для прямой инициализации переписать его как

static ClassA WHITE(1,1,whitePixel); 

Тем не менее, конструктор копирование по-прежнему следует принимать константную ссылку или даже удалить, как это было предложено 0x499602D2.

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