为什么不推荐使用 strtok()?
Why should strtok() be deprecated?
我从很多程序员那里听说,在不久的将来可能会弃用 strtok。有人说还是。为什么这是一个糟糕的选择?
strtok() 在标记给定字符串方面非常有效。它与时间和 space 复杂性有什么关系吗?
我在互联网上找到的最好 link 是 this。但这似乎并不能解决我的好奇心。如果可能,建议任何替代方案。
strtok(char *str, const char *delim)
的局限性在于它不能同时处理多个字符串,因为它维护一个静态指针来存储索引直到它被解析(因此如果一次只播放一个字符串就足够了).更好更安全的方法是使用 strtok_r(char *str, const char *delim, char **saveptr)
,它显式地使用第三个指针来保存解析后的索引。
Why is it a bad choice?
通过编程解决问题的基本技术是构造抽象,可以可靠地解决子问题,然后将这些子问题的解决方案 组合成更大问题的解决方案。
strtok 的行为以多种方式直接违背这些目标;这是一个糟糕的抽象,不可靠,因为它的组合很糟糕。
标记化的基本问题是:给定字符串中的一个位置,给出从该位置开始的标记结束位置。如果 strtok 只这样做,那就太好了。它会有一个清晰的抽象,它不会依赖隐藏的全局状态,它不会修改它的输入。
要了解 strtok 的局限性,想象一下尝试对一种语言进行标记化,我们希望用 spaces 分隔标记,除非标记包含在 "
"
中在这种情况下,我们希望对引用区域的内容应用不同的标记化规则,然后使用 space 分隔规则进行选择。 strtok 自身的组合很差,因此仅对最琐碎的标记化任务有用。
Does it have to do anything with the time and space complexities?
没有
Suggest any alternatives if possible.
词法分析器不难写;只写一个!
如果你写了一个不可变的词法分析器,奖励积分。不可变词法分析器是一个小结构,它包含对被词法分析的字符串的引用、词法分析器的当前位置以及词法分析器所需的任何状态。要提取一个标记,你调用一个 "next token" 方法,传入词法分析器,然后你得到标记 和一个新的词法分析器 。然后可以使用新的词法分析器对 下一个 标记进行词法分析,如果愿意,可以丢弃之前的词法分析器。
不可变的词法分析器技术比修改状态的词法分析器更容易推理。您可以通过将丢弃的词法分析器保存在列表中来调试它们,现在您可以立即查看完整的标记化操作历史记录。
我从很多程序员那里听说,在不久的将来可能会弃用 strtok。有人说还是。为什么这是一个糟糕的选择? strtok() 在标记给定字符串方面非常有效。它与时间和 space 复杂性有什么关系吗? 我在互联网上找到的最好 link 是 this。但这似乎并不能解决我的好奇心。如果可能,建议任何替代方案。
strtok(char *str, const char *delim)
的局限性在于它不能同时处理多个字符串,因为它维护一个静态指针来存储索引直到它被解析(因此如果一次只播放一个字符串就足够了).更好更安全的方法是使用 strtok_r(char *str, const char *delim, char **saveptr)
,它显式地使用第三个指针来保存解析后的索引。
Why is it a bad choice?
通过编程解决问题的基本技术是构造抽象,可以可靠地解决子问题,然后将这些子问题的解决方案 组合成更大问题的解决方案。
strtok 的行为以多种方式直接违背这些目标;这是一个糟糕的抽象,不可靠,因为它的组合很糟糕。
标记化的基本问题是:给定字符串中的一个位置,给出从该位置开始的标记结束位置。如果 strtok 只这样做,那就太好了。它会有一个清晰的抽象,它不会依赖隐藏的全局状态,它不会修改它的输入。
要了解 strtok 的局限性,想象一下尝试对一种语言进行标记化,我们希望用 spaces 分隔标记,除非标记包含在 "
"
中在这种情况下,我们希望对引用区域的内容应用不同的标记化规则,然后使用 space 分隔规则进行选择。 strtok 自身的组合很差,因此仅对最琐碎的标记化任务有用。
Does it have to do anything with the time and space complexities?
没有
Suggest any alternatives if possible.
词法分析器不难写;只写一个!
如果你写了一个不可变的词法分析器,奖励积分。不可变词法分析器是一个小结构,它包含对被词法分析的字符串的引用、词法分析器的当前位置以及词法分析器所需的任何状态。要提取一个标记,你调用一个 "next token" 方法,传入词法分析器,然后你得到标记 和一个新的词法分析器 。然后可以使用新的词法分析器对 下一个 标记进行词法分析,如果愿意,可以丢弃之前的词法分析器。
不可变的词法分析器技术比修改状态的词法分析器更容易推理。您可以通过将丢弃的词法分析器保存在列表中来调试它们,现在您可以立即查看完整的标记化操作历史记录。