我有一个程序可以检查键盘上读到的句子是否是英文字母。
但是,当显示结果时(在最后一个for
循环中),它超出了预期范围。如果取消注释该printf
语句,则可以看到即使i<26
将think设置为循环条件,它也会运行到最大,i = 27
并且大小为26的数组具有元素cache[26] = garbage value
和cache[27] = 0
。我的上一个for循环有什么问题?
int main() {
char* string = (char*)malloc(1024*sizeof(char));
fgets(string, 1024, stdin);
int i=0, cache[25]={0};
while(string[i]!='\0' ){
cache[(toupper(string[i])-'A')]++;
i++;
}
for( i=0; i<26; i++){
// printf("%d - %d\n",i,cache[i]);
if(!cache[i]){
printf("not pangram");
return(0);
}
}
printf("pangram");
return 0;
}
问题是您的数组首先对于26个字母而言太小。应该至少是cache[26]
。
然后,对于任何非字母字符(逗号,空格等),以下内容可能超出范围:
cache[(toupper(string[i])-'A')]++;
超出范围将损坏您的内存(例如,覆盖i或未定义行为时可能发生的其他情况)。
该如何解决呢?
您可以考虑保护您的缓存增量:
if (isalpha(string[i]))
cache[(toupper(string[i])-'A')]++;
请注意,某些更特殊的语言环境可能会将'A'-'Z'范围之外的某些字符视为字母。因此,您甚至可能想要更严格:
int letter=toupper(string[i])-'A';
if (letter>=0 && letter<26)
cache[(toupper(string[i])-'A')]++;
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句