侧边栏壁纸
博主头像
张种恩的技术小栈博主等级

行动起来,活在当下

  • 累计撰写 747 篇文章
  • 累计创建 65 个标签
  • 累计收到 39 条评论

目 录CONTENT

文章目录

C库函数-strtok

zze
zze
2024-03-27 / 0 评论 / 0 点赞 / 12 阅读 / 3955 字

不定期更新相关视频,抖音点击左上角加号后扫一扫右方侧边栏二维码关注我~正在更新《Shell其实很简单》系列

strtok 函数用于将一个大字符串分割成多个子字符串(标记)。每次调用 strtok 函数都会返回下一个标记(子字符串),直到没有更多的标记为止。

函数原型:

char *strtok(char *restrict s, const char *restrict delim);
  • s: 指向待分割字符串的指针。首次调用时,应指向要分割的整个字符串;后续调用时,应当传入NULL,strtok会继续从上一次的位置开始查找。

  • delim: 指向一个包含分隔符字符的字符串,strtok 将这些字符作为分割点。

行为特点:

  • strtok 在找到一个分隔符后,会将其替换为 '\0' 字符(空字符),从而使得当前标记成为一个独立的字符串。

  • 内部维护了一个静态变量来跟踪上次分割的位置,所以连续调用 strtok 可以遍历整个字符串的所有标记。

注意:

  • 使用 strtok 时要注意线程安全问题,因为它使用了静态存储区保存状态。在多线程环境中应考虑使用 strtok_r(POSIX扩展)或 strtok_s(在C11标准中定义的安全版本)。

示例:

  • 例 1:普通写法。

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

int main()
{
    char str[] = "Hello, World! This is a test string.";
    char delimiters[] = ", .! ";
    char *result_arr[32] = {};

    int idx = 0;
    // 首次调用,传递待分割字符串的首地址
    result_arr[idx] = strtok(str, delimiters);
    while (result_arr[idx] != NULL)
    {
        // 继续查找下一个标记,此时传入NULL
        result_arr[++idx] = strtok(NULL, delimiters);
    }

    idx = 0;
    while (result_arr[idx] != NULL)
    {
        printf("%s\n", result_arr[idx++]);
    }
}
  • 例 2:简写。

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

int main()
{
    char str[] = "Hello, World! This is a test string.";
    char delimiters[] = ", .! ";
    char *result_arr[32] = {str};

    int idx = 0;
    while ((result_arr[idx] = strtok(result_arr[idx], delimiters)) && ++idx)
        ;

    idx = 0;
    while (result_arr[idx] != NULL)
    {
        printf("%s\n", result_arr[idx++]);
    }
}
  • 例 3:封装成函数。

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

int msg_deal(char *msg_src, char *msg_done[], char delemiters[])
{
    int len = 0;
    while ((msg_done[len] = strtok(msg_done[len], delemiters)) && ++len)
        ;
    return len;
}

int main()
{
    char str[] = "Hello, World! This is a test string.";
    char *result_arr[32] = {str};
    int len = msg_deal(str, result_arr, ", .! ");
    // printf("len: %d\n", len); // 7
    int i = 0;
    while (result_arr[i] != NULL)
    {
        printf("%s\n", result_arr[i++]);
    }
}

例 1 和 例 2 的结果相同,运行代码后,输出将是:

Hello
World
This
is
a
test
string

每个单词都被当作单独的标记打印出来,这是因为逗号、句号、感叹号和空格都是我们的分隔符。

0

评论区