使用带有指针的strtok函数出现意外错误

时间:2014-12-15 16:36:32

标签: c visual-studio-2012 strtok

我只想了解strtok()功能如何在下面运作:

#define _CRT_SECURE_NO_WARNINGS
#include <stdlib.h>
#include <stdio.h>
#include <string.h>

int main(){
    char* p="abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";
    char* q=strtok(p, ",");
    printf("%s", q);

    return 0;
}

我试图运行这个简单的代码,但我一直得到一个我无法理解的奇怪错误。 这是我不断得到的错误:

screen shot

它可能不相关但是因为我的命令提示符不断退出我在项目中更改了一些设置并在某处添加了这行Console (/SUBSYSTEM:CONSOLE)我尝试在没有调试的情况下运行程序;甚至运行程序然后我尝试调试,这就是我如何在链接中得到错误。

4 个答案:

答案 0 :(得分:3)

而不是

char* p="abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";

使用

char p[] = "abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";

因为,根据strtok()的{​​{3}},它可能会修改输入字符串。在您的代码中,字符串文字为read-only。这就是它产生分段错误的原因。

相关引用:

  

使用这些功能时要小心。如果您确实使用它们,请注意:

     

*   这些函数修改了他们的第一个参数。

答案 1 :(得分:2)

char* p="abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";正在为p分配只读内存。确实p的类型应为const char*

尝试以任何方式更改该字符串会产生未定义的行为。所以在它上面使用strtok是一件非常糟糕的事情。要解决问题,请使用

char p[]="abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";

在堆栈上分配字符串并允许对其进行修改。 p 在某些情况下将衰减到指针;其中一个作为strtok的参数。

答案 2 :(得分:2)

您不能将字符串文字与函数strtok一起使用,因为该函数会尝试将传递给它的字符串更改为参数。

任何更改字符串文字的尝试都会导致未定义的行为。

根据C标准(6.4.5字符串文字)

  

7未指明这些阵列是否与它们不同   元素具有适当的值。 如果程序尝试   修改这样的数组,行为是未定义的。

更改此定义

char* p="abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";

char s[] = "abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";
//...
char* q = strtok( s, "," );

例如,函数main可以看起来像

int main()
{
    char s[] = "abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";
    char* q = strtok( s, "," );

    while ( q != NULL )
    {
        puts( q );
        strtok( NULL, "," );
    }

    return 0;
}

答案 3 :(得分:2)

首先解决错误:Segmentation fault
char *p更改为char p[]

原因是因为strtok()会在找到令牌字符时添加'\0'字符串分隔符。 在您的情况下,char* p="abc,def,ghi,jkl,mno,pqr,stu,vwx,yz";作为字符串文字存储在程序的只读部分。

当您尝试修改只读位置时会导致Segmentation fault