字符分割函数strtok

Posted Shemesz

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了字符分割函数strtok相关的知识,希望对你有一定的参考价值。

一、strtok()基本使用和介绍

1、函数原型

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

2、参数

  • str—要被分解的字符串
  • delim—用作分隔符的字符(可以是一个,也可以是集合)

3、返回值

  • 该函数返回被分解的第一个子字符串,若无可检索的字符串,则返回空指针

4、实例代码

#include <string.h>
#include <stdio.h>
 
int main () {
   char str[80] = "aaa - bbb - ccc";
   const char s[2] = "-";   //字符串里可以是一个分隔符,也可以是分隔符的集合
   char *token;
   
   /* 获取第一个子字符串 */
   token = strtok(str, s);
   
   /* 继续获取其他的子字符串 */
   while( token != NULL ) {
      printf( "%s\\n", token );
    
      token = strtok(NULL, s);
   }
   
   return(0);
}

编译运行
在这里插入图片描述
在这里我们可以看出strtok的基本使用方法

  1. 第一次调用strtok(),传入的参数str是要被分割的字符串{aaa - bbb -ccc},而成功后返回的是第一个子字符串{aaa};

  2. 而第二次调用strtok的时候,传入的参数应该为NULL,使得该函数默认使用上一次未分割完的字符串继续分割 ,就从上一次分割的位置{aaa-}作为本次分割的起始位置,直到分割结束。

二、strtok()注意事项

(1)delim 替换成 \\0

  • 在这个函数里strtok()在分解字符串的时候,第一个参数str是在不断变化的,这个函数是在改变原字符串,把原字符串{aaa - bbb - ccc}通过第二个参数delim将所有的分割符{-}替换成字符串结束标志字符{\\0},则原字符串变化为{aaa \\0 bbb \\0 ccc}
  • 错误示例:
#include <string.h>
#include <stdio.h>
 
int main () {
   char  *str = "aaa - bbb - ccc"; //****注意这里!
   const char s[2] = "-";
   char *token;
   
   /* 获取第一个子字符串 */
   token = strtok(str, s);
   
   /* 继续获取其他的子字符串 */
   while( token != NULL ) {
      printf( "%s\\n", token );
    
      token = strtok(NULL, s);
   }
   
   return(0);
}

注意:在这里,我实现函数的时候将字符串数组直接用指针指向它了,结果运行错误,后面发现虽然第一个参数是可以传指针,但我们要考虑空间内存布局,在strtok()函数里是delim的{分隔符}替换{ \\0}改变原字符串,而我们用指针指向这个字符串的时候,其实指向的是字符串常量,它的内存分布在文字常量区是不可被改变的,所以出现了错误!
在这里插入图片描述

(2)delim分隔符

  • strtok()的第二个参数delim,我看了很多博客都使用一个分隔符的示例,其实delim里可以是所有分隔符的集合,比如{aaa - bbb ; ccc | ddd},第二个参数delim可以是{-;|},用一个或多个分隔符去分解字符串都可以

(3)delim分隔符可不可以出现在第一个字符?

  • 答案是:可以
    当strtok分解的字符串首字符就是分隔符,那么strtok()会忽略首个分隔符,直接从第二个分隔符往下继续分解,例如:{- aaa - bbb - ccc} 那么strtok()会忽略第一个{-},还是以{aaa - bbb - ccc}的字符串形式继续分解。

三、strtok()函数源码

有的小伙伴可能想了解源码,在这里也贴上

char *strtok(char *str,const char *delim)
{
    static char *next_start = NULL;  //保存到静态存储区,函数返回后不会被销毁

    if(str == NULL && (str = next_start) == NULL)
    {
        return NULL;
    }

    char       *s = str;
    const char *t = NULL;

    while(*s)
    {
        t = delim;

        while(*t)
        {
            if(*t == *s)
            {
                next_start = s + 1;

                if(s == str)    //第一个字符就是分隔符
                {
                    str = next_start;
                    break;
                }
                else
                {
                    *s = '\\0';
                    return str;
                }
            }
            else
            {
                t++;
            }
        }

        s++;
    }

    return NULL;
}

关于这个函数在项目编程中需要经常使用,所以就搜集资料整理成自己的学习笔记了,如有不对,留言改正!

以上是关于字符分割函数strtok的主要内容,如果未能解决你的问题,请参考以下文章

字符串分割函数strtok(线程不安全),线程安全函数strtok_r

字符分割函数strtok

VC实现字符串分割的函数strtok

c语言的split字符串分割(函数strtok)

c语言的split字符串分割(函数strtok)

C语言最短时间带你实现strtok,字符串分割函数,建议收藏!!!