You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用strtok_s时第二个值始终为NULL,如何获取两个分割值?

问题

在C语言中使用strtok_s函数拆分空格分隔的用户输入时,始终只能获取第一部分,第二部分的值始终为NULL。目标是将输入拆分为两部分并通过指针返回,例如输入cd C://时,期望得到第一部分为cd,第二部分为C://,但实际第二部分始终为空。

原代码如下:

void argGetter(char* commandDesired, char** firstArg, char** secondArg) {
    // this char holds the first part of the command before the " "
    char* commandCleanDesired;
    // this char array holds the part after the " "
    char *nextToken;
    char *argument;
    commandCleanDesired = strtok_s(commandDesired, " ", &nextToken);
    argument = strtok_s(NULL, " ", &nextToken);
    printf("\n\nCMD 1 is %s\n\nCMD 2 is %s\n\n\n", commandCleanDesired, argument);
    *firstArg = commandCleanDesired;
    *secondArg = argument;

}

//this shows how argGetter is called.

void main() {
// these hold the return values from argGetter() 
    char* secondArg = NULL;
    char* firstArg = NULL;
//This holds user input
    char commandDesired[255];

    //This line prints the prompt
    printf("\n\tSanity$hell> ");
    //Then we get user input
    scanf_s("%s", commandDesired, 255);

    
    
    //split the command from args using argGetter
    argGetter(commandDesired, &firstArg, &secondArg);
    printf("\n First Arg is %s\n", firstArg);
    printf("\nYour second arg is %s\n\n", secondArg);

}

尝试过的修改(均未成功):

commandCleanDesired = strtok_s(commandDesired, " ", &commandDesired);
argument = strtok_s(commandDesired, " ", &commandDesired);
//the above resulted in NULL for the second value argument as well.
// Below is the next thing i tried.
char * nextToken;
commandCleanDesired = strtok_s(commandDesired, " ", &nextToken);
argument = strtok_s(NULL, " ", &nextToken);
//both result in argument being NULL. 
//I tried the above after reading the manual more.

问题原因

核心错误不在strtok_s的使用,而是输入读取阶段的问题:

  • scanf_s("%s", ...)会在遇到空格、换行符等空白字符时停止读取,所以当输入cd C://时,commandDesired中只会存储cd,后面的C://根本没被读入。
  • 后续调用strtok_s时,字符串里只有cd,自然拆分不出第二个token,返回NULL。

修复方案

替换scanf_s为能读取包含空格的整行输入的函数,比如fgets,同时注意处理fgets会读取换行符的问题。修改后的完整代码如下:

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

void argGetter(char* commandDesired, char** firstArg, char** secondArg) {
    char* commandCleanDesired;
    char *nextToken;
    char *argument;
    
    // 去掉fgets读入的换行符
    size_t len = strlen(commandDesired);
    if (len > 0 && commandDesired[len-1] == '\n') {
        commandDesired[len-1] = '\0';
    }
    
    commandCleanDesired = strtok_s(commandDesired, " ", &nextToken);
    argument = strtok_s(NULL, " ", &nextToken);
    
    printf("\n\nCMD 1 is %s\n\nCMD 2 is %s\n\n\n", commandCleanDesired, argument);
    *firstArg = commandCleanDesired;
    *secondArg = argument;

}

int main() { // 标准main返回类型为int
    char* secondArg = NULL;
    char* firstArg = NULL;
    char commandDesired[255];

    printf("\n\tSanity$hell> ");
    // 使用fgets读取整行输入,包含空格
    fgets(commandDesired, sizeof(commandDesired), stdin);
    
    argGetter(commandDesired, &firstArg, &secondArg);
    printf("\n First Arg is %s\n", firstArg);
    printf("\nYour second arg is %s\n\n", secondArg);
    
    return 0;
}

补充说明:

  • fgets会把输入的换行符也读进数组,手动替换为\0可以避免后续处理出现异常。
  • 标准C规范中main函数的返回类型应为int,而非void,修正后更符合代码规范。

内容的提问来源于stack exchange,提问作者BoundedLeap

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.06 13:50:30