strtok() - 为什么你必须传递NULL指针才能获得字符串中的下一个标记?

时间:2015-04-14 22:39:21

标签: c++ c string pointers strtok

这是对strtok()的解释。

#include <string.h>
char* strtok( char* s1, 
              const char* s2 );*
  

第一次调用strtok()会返回指向第一个标记的指针   s1指向的字符串。对strtok()的后续调用必须传递NULL   指针作为第一个参数,以获取下一个标记   字符串。

但我不知道,为什么你必须传递NULL指针才能获得字符串中的下一个标记。我搜索了大约15分钟,但没有在互联网上找到解释。

2 个答案:

答案 0 :(得分:38)

strtok()通过使用静态变量将一些数据保留在自身内部。这样,strtok()可以继续从上一次通话中停止的点开始搜索。要通知strtok()您要继续搜索相同的字符串,请传递NULL指针作为其第一个参数。 strtok()检查第一个参数是否为NULL,如果是,则使用其当前存储的数据。如果第一个参数不为null,则将其视为新搜索,并重置所有内部数据。

您可以做的最好的事情是搜索strtok()函数的实际实现。我发现一个小到足以在这里发布它,所以你知道如何处理这个NULL参数:

/* Copyright (c) Microsoft Corporation. All rights reserved. */

#include <string.h>

/* ISO/IEC 9899 7.11.5.8 strtok. DEPRECATED.
 * Split string into tokens, and return one at a time while retaining state
 * internally.
 *
 * WARNING: Only one set of state is held and this means that the
 * WARNING: function is not thread-safe nor safe for multiple uses within
 * WARNING: one thread.
 *
 * NOTE: No library may call this function.
 */

char * __cdecl strtok(char *s1, const char *delimit)
{
    static char *lastToken = NULL; /* UNSAFE SHARED STATE! */
    char *tmp;

    /* Skip leading delimiters if new string. */
    if ( s1 == NULL ) {
        s1 = lastToken;
        if (s1 == NULL)         /* End of story? */
            return NULL;
    } else {
        s1 += strspn(s1, delimit);
    }

    /* Find end of segment */
    tmp = strpbrk(s1, delimit);
    if (tmp) {
        /* Found another delimiter, split string and save state. */
        *tmp = '\0';
        lastToken = tmp + 1;
    } else {
        /* Last segment, remember that. */
        lastToken = NULL;
    }

    return s1;
}

答案 1 :(得分:12)

如果传递非NULL值,则要求它开始标记不同的字符串。

如果传递NULL值,则要求继续像以前那样标记化。