我有一个字符串,我想把它分成几个单词。当传递的字符串以空格结尾时,代码会起作用,否则
不起作用。代码:
void form_rule2(char * str)
{
int num_words=0;
char word[20];
while(sscanf(str,"%s",word)==1)
{
num_words++;
printf("%sn",word);
str+=strlen(word)+1;
}
}
void main()
{
form_rule2("abcd efgh! ijkl mnop");
}
我得到的输出是:
abcd
efgh!
ijkl
mnop
P
显然' p '是额外的,其他测试用例的情况也类似,在末尾给出随机字符。
我想知道这里发生了什么,是否涉及到NULL终止字符。
我在linux上使用gcc编译器和x86-64处理器,如果有关系的话。
问题在这里:
str+=strlen(word)+1;
跳过当前单词及其后面的空格。
如果字符串中的最后一个单词没有尾随空格字符,则实际上跳过该单词以及结束字符串的尾随' '字符。然后解析数组后面的任何垃圾。
从技术上讲,你通过访问超出数组边界调用未定义行为。
一种可能的解决方案是检查末尾是否有空白字符,如果有,只跳过。
str+=strlen(word);
if (isspace(*str))
++str;
你需要#include <ctype.h>
.
请注意,这不是非常健壮的东西,如在一行中有多个空格,但这是一个单独的问题。