【问题标题】:Why isn't strtok correctly separating tokens?为什么 strtok 不能正确分离标记?
【发布时间】:2013-05-23 07:22:02
【问题描述】:

我正在尝试调整以下工作代码:

http://www.cplusplus.com/reference/cstring/strtok/

如下:

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

int main (int argc, const char * argv[]) {

    char input[10];   
    scanf("%s", input);
   char * pch;
   pch = strtok(input, " ");

 while (pch != NULL)
  {
    printf ("%s\n",pch);
    pch = strtok(NULL, " ");
  }   

   return 0;
}

如果我输入

test string to tokenize

我只会回来

test

我做错了什么?

【问题讨论】:

    标签: c string strtok


    【解决方案1】:

    %s 转换在第一个空格处停止。

    在调用strtok() 之前打印你的字符串;只会是"test"

    另外,正如@Paul R 所指出的,您需要考虑正在使用的缓冲区大小。 10 个字符非常小。

    【讨论】:

      【解决方案2】:
      scanf("%s", input);
      

      这个有几个问题:

      1. %s 转换说明符使scanf() 一直扫描到第一个空格。你在缓冲区中得到的只是test

      2. test string to tokenize 不能容纳 10 个字符。

      使用fgets() 代替适当大小的缓冲区:

      char buf[LINE_MAX];
      fgets(buf, sizeof(buf), stdin);
      

      另一条建议:使用strtok_r() 而不是strok(),这样更安全。

      char *endp;
      char *p = strtok_r(buf, " ", &endp);
      while (p) {
          puts(p);
          p = strtok_r(NULL, " ", &endp);
      }
      

      【讨论】:

      • strtok_r 是可重入的,如果您正在编写库或使用线程,它很有用,否则 strtok 很好。
      【解决方案3】:

      尝试将字符串“test string to tokenize”存储在char[10] 中会导致缓冲区溢出。在那之后,任何事情都可能发生。增加input的大小:

      char input[256];
      

      另外,正如@H2CO3 所述,您应该使用fgets(...) 而不是scanf("%s", ...),以避免出现空白问题。

      【讨论】:

        【解决方案4】:
        scanf("%s", input);
        

        这需要输入,直到遇到空格或 \n 。事实上,您只向 strtok 输入“测试”作为参数。

        您需要使用getline 之类的东西来输入带空格的行。

        另外,正如其他人所指出的,您的缓冲区可能会溢出。

        【讨论】:

          猜你喜欢
          • 2022-11-16
          • 2017-08-03
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-12-06
          相关资源
          最近更新 更多