strtol、strtoll和strtod对于任何字符,即使没有以null结尾,是否安全?

7

我正在尝试将一些字符转换为数字类型,但其中一些可能不是以空字符结尾的字符串。那么对于这些没有以空字符结尾的字符串,strtol、strtoll、strtod 是否安全?

2个回答

8

不带空字符结尾的字符数组就不是一个字符串。如果任何strto*()函数传递的参数不指向字符串,则行为未定义。

参考2011年ISO C标准的最新草案:

7.1.1术语定义:

一个字符串是一个由第一个空字符终止并包括在内的字符连续序列。

7.1.4库函数的使用:

如果函数的参数具有无效值(例如函数域之外的值,程序地址空间之外的指针,空指针或指向非可修改存储器的指针,而相应的参数没有const限定符)或类型(升级后)与变量数量的函数不匹配,则行为未定义。

7.22.1.3 strtodstrtofstrtold函数:

strtodstrtofstrtold函数分别将nptr指向的字符串的初始部分转换为doublefloatlong double表示。

(已加重强调)

因此,不指向字符串的参数超出了函数的域。

如果数组包含类似{ '1','2','3','x','y','z' }的内容,则可能会得逞,因为它不需要扫描超过终止所需值的x,但行为明确未定义。

如果要使用这些函数,应将数组复制到另一个缓冲区中并显式地自己终止空字符。


0
只要您的输入以某种方式终止,而这绝对不是有效的数字字符,处理过程就会停止,并且不应该一直快乐地读取内存,直到找到第一个NUL。
所以我认为你没问题。

例如,转换后的数字后面如果是空格、标点符号或者不包含该字母的字母,则扫描将停止。 - Jonathan Leffler
@JonathanLeffler:除了前导空格、小数点和其他可能是有效输入的内容,是的。 - Ben Voigt
@Ben - 我及时修正了我的评论,加上了“转换后的数字之后”的部分,这在第一版中明显缺失,而且绝对是必要的。 - Jonathan Leffler
2
@BenVoigt:理论上来说它是不应该的,但标准中并没有保证它不会发生。 - Keith Thompson

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接