在数组中对signed和unsigned char进行索引的区别是什么?

时间:2014-09-15 20:33:39

标签: c arrays char

我必须遵循代码,而这些代码并没有产生我预期的结果。添加unsigned char会使它工作。 (我意识到它不能通过另一个功能做反向,但没有得到相反的效果!) 有人可以向我解释一下。

代码是将8个char字符串替换为一些随机字符。

我目前的代码:

char subs[8][256];

void perfSubs(char* input){
for (int i = 0; i < 8; i++)
    input[i] = subs[i][input[i]];
}

我应该把它改成

input[i] = subs[i][(unsigned char)input[i]];

3 个答案:

答案 0 :(得分:2)

正如其他人所提到的,众所周知C有unsigned charsigned charchar类型。
char的范围与unsigned charsigned char的范围相同,但仍然是不同的类型。

subs[i][input[i]];可能会涉及subs[i][some_negative_value]问题的负面索引。

input[i] = subs[i][(unsigned char)input[i]];将负值折叠成可能来自input[i]的正值,但这是实现定义的行为方式。

只需使用char即可获得一个简单的解决方案。


要避免使用否定索引,只要代码使用char作为索引,就减去最小CHAR_MINcharCHAR_MIN的典型值为0或-128。

还要避免幻数256并使用基于char的数组大小。

char subs[8][CHAR_MAX + 1 - CHAR_MIN];

input[i] = subs[i][input[i] - CHAR_MIN];

取决于char是否已签名,使用索引'A'的位置可能会导致不同的索引,尽管在给定的编译中是一致的。

subs[0]['A' - CHAR_MIN] = 'x';

答案 1 :(得分:1)

标准没有规定char是签名类型还是无符号类型。它可以在一个平台上签名,在另一个平台上签名。如果您希望代码可移植,请选择一种您可以依赖的类型。

在您的情况下,您应该使用:

void perfSubs(unsigned char* input){
for (int i = 0; i < 8; i++)
    input[i] = subs[i][input[i]];
}

这可以确保您获得unsigned char*函数,而不必依赖char类型是带符号类型还是无符号类型。

答案 2 :(得分:0)

signed char可以保存-128到127之间的值。由于您使用该字节存储0到255之间的值,因此需要一个unsigned char。