C ++错误:将'char *'赋值给'char [2]的类型不兼容

时间:2013-04-09 23:15:03

标签: c++ error-handling char

我的构造函数有点问题。 在我的头文件中,我声明:

char short_name_[2]; 
  • 和其他变量

在我的构造函数中:

Territory(std::string name, char short_name[2], Player* owner, char units);
void setShortName(char* short_name);
inline const char (&getShortName() const)[2] { return short_name_; }

在我的cpp文件中:

Territory::Territory(std::string name, char short_name[2], Player* owner, 
                     char units) : name_(name), short_name_(short_name), 
                    owner_(owner), units_(units)
{ }

我的错误:

  

Territory.cpp:在构造函数'Territory :: Territory(std :: string,   char *,Player *,char)':Territory.cpp:15:33:错误:不兼容的类型   将'char *'赋给'char [2]'

我已经发现了char[2] <=> char*,但我不知道如何处理有关我的构造函数和get / setter的内容。

3 个答案:

答案 0 :(得分:15)

C ++中的原始数组有点烦人,充满了危险。这就是为什么除非你有充分理由要使用std::vectorstd::array

首先,正如其他人所说,char[2]char*不同,或者至少通常不同。 char[2]char的2号数组,char*是指向char的指针。它们经常会混淆,因为数组会在需要时衰减到指向第一个元素的指针。所以这有效:

char foo[2];
char* bar = foo;

但反过来却没有:

const char* bar = "hello";
const char foo[6] = bar; // ERROR

引起混淆时,在声明函数参数时,char[]等同于char*。因此,在构造函数中,参数char short_name[2]实际上是char* short_name

数组的另一个怪癖是它们不能像其他类型一样被复制(这是为什么函数参数中的数组被视为指针的原因之一)。例如,我可以做这样的事情:

char foo[2] = {'a', 'b'};
char bar[2] = foo;

相反,我必须迭代foo的元素并将它们复制到bar,或者使用一些为我这样做的函数,例如std::copy

char foo[2] = {'a', 'b'};
char bar[2];
// std::begin and std::end are only available in C++11
std::copy(std::begin(foo), std::end(foo), std::begin(bar));

因此,在构造函数中,您必须手动将short_name的元素复制到short_name_中:

Territory::Territory(std::string name, char* short_name, Player* owner, 
                     char units) : name_(name), owner_(owner), units_(units)
{ 
    // Note that std::begin and std::end can *not* be used on pointers.
    std::copy(short_name, short_name + 2, std::begin(short_name));
}

正如您所看到的,这一切都非常烦人,所以除非您有充分的理由,否则您应该使用std::vector而不是原始数组(或者在这种情况下可能是std::string)。

答案 1 :(得分:2)

当一个函数想要一个数组作为参数时,它会得到一个指向数组第一个元素的指针。此指针不能用于初始化数组,因为它是指针,而不是数组。

您可以将接受引用的函数编写为数组作为参数:

void i_dont_accept_pointers(const char (array&)[2]) {}

这里的问题是,这个数组引用不能用于初始化另一个数组。

class Foo {
  char vars[2];
  Foo(const char (args&)[2])
    : vars(args)  // This will not work
  {}
};

C ++ 11引入了std::array来消除数组的这个问题和其他问题。在旧版本中,您必须遍历数组元素并单独复制它们或使用std::copy

答案 2 :(得分:0)

C ++作为C拥有C的大部分规则。

对于C语言,请始终使用char *传递数组,因为C语言如何看待它。传递给函数时,即使this.categories$ = this._categoryService.getAll() .pipe( finalize(() => this.loading = false) ); 也将是8或4。 现在,变量sizeof (short_name_)

中有2个字节的空间

构造函数在short_name_中为两个字节分配了内存,您需要将字节复制到其中或使用char *指针并假定其大小为2。

专家C编程:Deep C的秘密中的第9章很容易理解。

为简单起见,这可能是C样式代码。

short_name_