我想知道之间有什么区别:
let b = read_int();;
和
let scan_int () = Scanf.scanf " %d" (fun x -> x)
?
此外,为什么Scanf将一个功能作为一个条目?
答案 0 :(得分:10)
read_int ()
读取整行,将整行更改为整数。整行必须只包含一个整数。
Scanf.scanf " %d" (fun x -> x)
也读取整行,在行的开头处删除空格,然后读取以十进制表示法写入的整数。如果该整数后面有字符,则将它们留在缓冲区中。
这是一张表:
| line in stdin | read_int | scanf " %d" |
|---------------|----------|-----------------|
| "1234" | 1234 | 1234 |
| " 1234" | ERROR | 1234 |
| "1234 foo" | ERROR | 1234 (foo left) |
| "0xff" | 255 | 0 (xff left) |
缓冲区中剩下的内容通常会妨碍您的下一次扫描。我建议你不要在未知输入上使用scanf。
关于所需的身份功能,这是因为scanf可能具有非常复杂的格式字符串,这将创建复杂的数据。您希望如何返回返回的数据无法猜到。可以使用元组,但OCaml在该特定情况下不支持任意扁平化产品。给予我们所谓的延续,可以很好地有效地完成工作。
答案 1 :(得分:3)
主要区别在于,如手册中所述,read_int
读取整行,并期望整行(当然最终\n
除外)包含整数,而与您的scan_int
的定义,整数后可以有一些非数字字符。
Scanf.scanf
的函数参数允许您对输入执行任意转换。
答案 2 :(得分:3)
简而言之,Scanf
模块提供了一种从抽象字符源读取多个输入的方法。例如,以下函数从字符串中读取由=
字符分隔的两个字符串输入:
let f string = Scanf.sscanf string "%s@=%s" (fun x y -> x, y )
assert (f "x=y" = "x","y")
函数参数提供了一种通用方法,将scanf函数读取的多个输入组合到一个输出中。
因此,read
中提供的少数Pervasives
函数的推广只能按行读取一个输入,而且只能读取Pervasives in_channel
。