字符* 和无符号字符* 之间不兼容

Incompatibility between char* and unsigned char*?

本文关键字:字符 不兼容 之间 无符号      更新时间:2023-10-16

以下代码行使用 HP-UX 的C++编译器生成编译器警告:

strcpy(var, "string")

输出:

error #2167: argument of type "unsigned char *" 
    is incompatible with parameter of type "char *"

请注意:var是这里的unsigned char * - 它的数据类型超出了我的控制范围。

两个问题:

  1. 在这两种类型的上下文中,不兼容意味着什么?如果编译器被迫接受转换,会发生什么情况?如能举个例子,将不胜感激。
  2. 假设我必须使用strcpy,使上述代码行正常工作的安全方法是什么?

C++严格检查std::strcpy期望char*的类型,而变量varunsigned char*

幸运的是,在这种情况下,将指针投射到如下所示的char*是完全安全的:

std::strcpy(reinterpret_cast<char*>(var), "string");

这是因为,根据标准,charunsigned charsigned char可以相互别名。

在 C 标准中,字符是 Impementation Defined。ANSI C 提供三种字符类型(这三种字符都占用一个字节(:字符、有符号字符、无符号字符。不只是像短,int,只有两个。

您可以尝试:

char *str="abcd"; signed char *s_str = str;

编译器将警告代码的第二行是错误的。它就像:

short num = 10; unsigned short *p_num = &num;

编译器也会发出警告。因为它们是编译器中定义的不同类型。

因此,如果您编写"strcpy( (char*(var,"string"(",代码只是将字符从"string"的空间复制到"var"的空间。这里是否存在错误取决于您如何处理"var"。因为"var"不是"char *"

charsigned charunsigned char是C++中的不同类型。 指向它们的指针是不兼容的 - 例如,强制编译器将unsigned char *转换为char *以便将其传递给strcpy()在某些情况下正式导致未定义的行为 - 当指针随后被取消引用时。 因此警告。

与其使用strcpy()(因此必须强制转换指针(,不如这样做(C++11 及更高版本(

const char thing[] = "string";
std::copy(std::begin(thing), std::end(thing), var);

没有未定义的行为。

更好的是,考虑使用标准容器,例如 std::vector<unsigned char>std::string ,而不是使用原始数组。 所有标准容器都提供了一种访问其数据的方法(例如,用于将合适的指针传递给遗留 API 中的函数(。