从类型'char *'分配类型'char [100]'时出现错误消息“不兼容的类型”

时间:2015-04-14 02:32:40

标签: c++ c arrays struct char

当从类型'char *'"中分配类型'char [100]'时,编译器给出了一个错误,"不兼容的类型;当我尝试执行以下行时:

records[i].address = records[i+1].address;

records是一个struct rec数组,其定义如下:

struct rec{
    char address[100];
}

为什么它会给我这个错误?左侧和右侧是相同的类型。

4 个答案:

答案 0 :(得分:2)

char[100]char *的类型不同。一个是包含100个字符变量的数组,另一个是包含字符变量地址的变量。

你可以"分配" char[100]char *只是因为"裸露的"数组求值为第一个元素的地址 - 地址不能包含任何内容 - 它不是变量,其中是变量。

因此,

char array[ 100 ];
char *ptr = array;

有效,而

char array[ 100 ];
char *ptr;
array=ptr;

没有。第一种情况是说ptr现在指向array的第一个元素。第二个是" array的地址应该被赋予ptr的值,这实际上是无意义的。

答案 1 :(得分:1)

您无法分配数组,如果您考虑它,那么复制数组的内容是没有意义的,假设它是' sa你需要strcpy()的字符串,例如

strcpy(records[i].address, records[i+1].address);

答案 2 :(得分:0)

之前的答案提到了char a[]char * a之间的区别。我想让它更干净。

char a[]中,a只表示一个数组地址,而不是一个变量,这意味着它无法分配。实际上, a将被编译为可执行文件时的最终地址替换。你不能为一个值赋值。

例如,

foo.c的:

char *myvar = "hello";

int 
main() {
    return myvar[0];
}

运行

gcc foo.c -o foo ; objdump -S foo

你会得到:

mov    0x2003ef(%rip),%rax      # put value of `myvar` into %rax

movzbl (%rax),%eax              # put *myvar into %eax

char *myvar = "hello"替换为char myvar[] = "hello"后,您只需获得一行:

movzbl 0x2003e7(%rip),%eax    # put address of array `myvar` into %eax

答案 3 :(得分:0)

首先,我将假设这个问题是关于C ++的,因为它标记了C ++。 C标签存在问题,因为C是与类似但不完全相同的规则的不同语言。对于编程,魔鬼就是细节。

现在,给定

int const n = ....;

struct rec{
    char address[100];
};

rec records[n];

你做不到

records[i].address=records[i+1].address;

因为原始数组不可分配。这是没有充分理由的,AFAIK。但可能主要的驱动因素是,在早期的C中,一个侧重于能够定义可以使用任何长度数组的函数,而Brian Kernighan ridiculed Pascal(使用数组赋值)则无法表达这些通常有用的函数。

另一方面,你可以做到

records[i]=records[i+1];

因为默认情况下可以分配类实例。

作为一种相反的情况(或类似的情况,取决于一个人关注的特性),当一个函数按值返回一个类实例时,它的赋值运算符允许你赋值给整个实例(因为成员函数可以是调用rvalues),但函数调用表达式的rvalue-ness会阻止您分配给基本类型成员。这些规则,一个关于数组成员和一个关于rvalue的规则,对于初学者来说似乎是非常随意的。他们是。 ; - )

无论如何,你应该做的是使用std::string而不是char的原始数组,如下所示:

struct rec{
    std::string address;
};

然后,您可以根据需要分配address成员或整个struct