strtok的功能和多线程 [英] strtok function and multithreading

查看:230
本文介绍了strtok的功能和多线程的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我读了有关的strtok(字符* S1,字符* S2)及其实施很多东西。但是,我仍然无法理解是什么使一个危险的功能多线程程序中使用。可有人请给我一个多线程程序的一个例子,解释这个问题呢?请不就是我要找显示我在哪里,问题就出现了一个例子。

I read a lot of stuff about strtok(char* s1, char* s2) and its implementation. However, I still can not understand what makes it a dangerous function to use in multi-threaded program. Can somebody please give me an example of a multi-threaded program and explain the issue there? Please not that I am looking for an example that shows me where the problem arises.

PS:strtok的(字符* S1,字符* S2)是C标准库的一部分。

ps: strtok(char* s1, char* s2) is part of the C standard library.

推荐答案

下面是一个具体的例子:

Here is a concrete example:

首先假设你的程序是多线程的,并且在执行一个线程,下面code运行:

Suppose first that your program is multi-threaded, and in one thread of execution, the following code runs:

char str1[] = "split.me.up";

// call this line A
char *word1 = strtok(str1, "."); // returns "split", sets str1[5] = '\0'

// ... 

// call this line B
char *word2 = strtok(NULL, "."); // we hope to get back "me"

和在另一个线程,以下code运行:

And in another thread, the following code runs:

char str2[] = "multi;token;string";

// call this line C
char *token1 = strtok(str2, ";"); // returns "multi", sets str2[5] = '\0'

// ...

// call this line D
char *token2 = strtok(NULL, ";"); // we hope to get back "token"

问题的关键是,我们真的不知道会在字词2 token2 什么:

如果该命令的顺序(A),(B),(C),(D)上运行,那么我们会得到我们想要的东西。

If the commands are run in the order (A), (B), (C), (D), then we will get what we want.

但如果说,命令中的顺序运行(A),(C),(B),(D),然后命令(B)将搜索记号;字符串!这是因为 NULL 第一个参数的命令(B)告诉 strtok的继续在搜索的最后一个非 - NULL 搜索字符串它被通过,因为命令(C)已经运行, strtok的将使用 STR2

But if, say, the commands run in the order (A), (C), (B), (D), then command (B) will search for a . delimeter in "token;string"! This is because the NULL first argument to command (B) tells strtok to continue searching in the last non-NULL search string it was passed, and because command (C) has already run, strtok will use str2.

然后命令(B)将返回标记;串,同时设置一个搜索到的 NUL <新起始字符/ code>终止在 STR2 的结束。然后命令(D)会认为这是寻找一个空字符串,因为这将开始其在的STR2 NUL 终止,所以会返回 NULL 以及

Then command (B) will return token;string, at the same time setting the new starting character of a search to the NUL terminator at the end of str2. Then the command (D) will think it is searching an empty string, because it will begin its search at str2's NUL terminator, and so will return NULL as well.

即使你把命令(A)和(B)紧挨着对方,并命令(C)和(D)紧挨着对方,也不能保证(B)会之后立即执行( A)之前是(C)或(D)等。

Even if you place commands (A) and (B) right next to each other, and commands (C) and (D) right next to each other, there is no guarantee that (B) will be executed right after (A) before either (C) or (D), etc.

如果你建立某种形式的互斥体或替代后卫的保护了 strtok的的功能,并且只调用 strtok的从已取得的锁的线程表示互斥,那么 strtok的可以放心使用。但是,它可能只是为了更好地使用线程安全的 strtok_r 正如其他人说。

If you create some sort of mutex or alternate guard to protect the use of the strtok function, and only call strtok from a thread which has obtained a lock on said mutex, then strtok is safe to use. However, it is probably better just to use the thread-safe strtok_r as others have said.

编辑:还有一个问题,就是别人没提,即 strtok的修改,并可能使用全局(或静态的,无论)变量,并在可能-不是线程安全的方式这样做,所以即使你不靠重复调用 strtok的来得到连续的令牌相同的字符串,也未必是安全的使用它在多线程环境中无人看守,等。

There is one more issue, that nobody else has mentioned, namely that strtok modifies and potentially uses global (or static, whatever) variables, and does so in a probably-not-thread-safe way, so even if you don't rely on repeating calls to strtok to get successive "tokens" from the same string, it may not be safe to use it in a multi-threaded environment without guards, etc.

这篇关于strtok的功能和多线程的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆