C strtok问题

时间:2018-03-13 18:49:07

标签: c linked-list strtok

我有一个链表并尝试将其中一个值分成两个不同的变量。我从包含"0000:c29302"的id变量开始,但我想将":"任意一侧的部分分解为clientid和token变量。 当我运行我的代码时,它会在split函数中进入while循环,但之后只会出现崩溃。谢谢!

typedef struct node {
    char *id;
    char *clientid;
    char *token;
    struct node * next;
} credentials;

void split(credentials * head, char *delim);

int main()
{
    credentials * head = NULL;
    head = malloc(sizeof(credentials));

    head->id = "0000:c29302";
    head->next = NULL;
    split(head, ":");
}

void split(credentials * head, char *delim)
{
    char *token;
    char *temp;
    credentials * current = head;
    while (current != NULL) { //THIS WHILE LOOP
        temp = current->id;
        token = strtok(temp, delim);
        while(token != NULL)
        {
            printf("%s\n", token);
            token = strtok(NULL, delim);
        }
        current = current->next;
    }
}

2 个答案:

答案 0 :(得分:4)

这种情况发生了,因为strtok()修改了字符串参数!由于您在此处使用字符串文字,因此很可能将其保存在平台上的只读内存中。因此,每次尝试修改它都会导致违反分段"。

如果您确定您的字符串是可修改的,例如使用

head->id = strdup("0000:c29302");

它应该按预期工作!

答案 1 :(得分:1)

当您查看函数声明时:

char *strtok(char *str, const char *delim)

您可能会注意到delim的类型为const char *,但str的类型为char *。 这是因为此字符串str的内容被修改并分解为更小的字符串(标记)

"0000:c29302"是一个字符串文字,其内容无法修改。

任何修改字符串文字的尝试通常都会导致运行时错误"Segmentation Violation".

您的strtok必须指向可以修改的内存位置。

因此,您应该为其分配内存并将字符串文字复制到其中。

您可以使用malloc

head->id = malloc(strlen("0000:c29302")+1); // 1 char more for string terminator
strcpy(head->id, "0000:c29302");

或使用char * strdup(const char *str1);

返回指向以null结尾的字节字符串的指针,该字符串是str1指向的字符串的副本。

head->id = strdup("0000:c29302");

在这两种情况下,必须在某个时刻释放字符串的已分配内存,以避免内存泄漏。