警告:数组下标的类型为'char'[-Wchar-subscripts]

时间:2015-02-13 23:47:22

标签: c arrays string char gcc-warning

当我使用gcc -Wall运行我的程序时,我正在

warning: array subscript has type ‘char’

请帮助我哪里出错了。警告说它在20:7& 21:7。我怎样才能摆脱警告?

/* This program asks the user for 2 words and tells the user if those 2 words
   are anagrams even if its capitalized or not. The maximum length of letters
   is 20.  */

#include<stdio.h>
#include<string.h>

int anagram(char* str1, char* str2)
{
    // Create two count arrays and initialize all values as 0
    int numOfChar = 20;
    char count1[123] = {0};
    char count2[123] = {0};
    int i;

    /* For each character in the strings, it increases in
       the corresponding count array */
    for (i = 0; str1[i] && str2[i];  i++)
    {
        count1[str1[i]]++;
        count2[str2[i]]++;
    }

    // If both strings are different lengths.
    if (str1[i] || str2[i]) // If one statement is true
    {
        return 0;
    }

    // Compares count arrays
    for (i = 0; i < numOfChar; i++)
    {
        if (count1[i] != count2[i]) // If dont equal to eachother
        {
            return 0;
        }

    }
    return 1;

}

// Construct function
void construct()
{
    int anagram(char*,char*); // Variables
    char str[20], str1[20];
    int check = 0;

    printf("Please enter the first word: ");
    scanf("%s", str);

    printf("Please enter the second word: ");
    scanf("%s", str1);


    check=anagram(str, str1);
    if (check==1)
    {               // If true then print
        printf("%s is an anagram of %s\n", str, str1);
    }
    else
    {               // If false then print
        printf("%s is NOT an anagram of %s\n", str, str1);
    }

    return ;
}

// Main function
int main()
{
  construct(); // Calls construct function
  return 0;
}

3 个答案:

答案 0 :(得分:1)

问题是字符串可能包含非us字符集中的字符(除了us-ascii之外的任何编码)。

其中表示为负值。我认为访问具​​有负索引的数组并不完全符合您的预期。

将其处理为:

    count1[(unsigned char)str1[i]]++;
    count2[(unsigned char)str2[i]]++;

会抑制警告,但仍然会超出范围。

将以下检查添加到for循环将终止循环,以防字符值完全出乎意料:

 str1[i] && str2[i] &&
 (unsigned char)str1[i] < countof(count1) &&
 (unsigned char)str2[i] < countof(count2)

countof定义为:

#define countof(x) sizeof(x)/sizeof(x[0])

答案 1 :(得分:0)

编译器正在为您提供有关第20行和第21行索引的警告

count1[str1[i]]++;
count2[str2[i]]++;

并且可疑索引来自函数参数。

int anagram(char* str1, char* str2)

请注意,它们指向char类型,默认情况下会签名。因此,如果您用于索引count1[]的数组中的一个元素具有0x800xFF范围内的值,则会导致使用负索引,这显然不在数组范围count1[]

虽然count1[]count2[]只有123个元素,所以你不期望实际的索引是负数,所以最好让数组通过{ {1}},因此该函数将声明为

unsigned char

然后你总会得到一个积极的指数。至于警告,MSVC不会给我一个,但是如果你然后将索引转换为int anagram(unsigned char* str1, unsigned char* str2) ,如下面的问题所述,那就应该处理它。

答案 2 :(得分:0)

编译器给出这样一个警告的原因是,在x[index]执行index是char类型时,通常是编程错误。

如果是您想要的,只需强制转换为int即可。例如,在您的代码中count1[(int)str1[i]]++;

请记住,打印数字'1'的字符不具有与1数字相等的值。忘记它,并假设它是,编译器警告将会发现的常见错误之一。