Skip to content

Commit

Permalink
第十二章修改 (#838)
Browse files Browse the repository at this point in the history
Co-authored-by: Joe Chen <[email protected]>
  • Loading branch information
loftea and unknwon authored May 12, 2022
1 parent e394361 commit d296444
Show file tree
Hide file tree
Showing 13 changed files with 83 additions and 83 deletions.
2 changes: 1 addition & 1 deletion eBook/12.0.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# 12.0 读写数据

除了 fmt 和 os 包,我们还需要用到 bufio 包来处理缓冲的输入和输出。
除了 `fmt``os` 包,我们还需要用到 `bufio` 包来处理缓冲的输入和输出。

## 链接

Expand Down
16 changes: 8 additions & 8 deletions eBook/12.1.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# 12.1 读取用户的输入

我们如何读取用户的键盘(控制台)输入呢?从键盘和标准输入 `os.Stdin` 读取输入,最简单的办法是使用 `fmt` 包提供的 Scan 和 Sscan 开头的函数。请看以下程序:
我们如何读取用户的键盘(控制台)输入呢?从键盘和标准输入 `os.Stdin` 读取输入,最简单的办法是使用 `fmt` 包提供的 `Scan...``Sscan...` 开头的函数。请看以下程序:

示例 12.1 [readinput1.go](examples/chapter_12/readinput1.go)

Expand Down Expand Up @@ -28,9 +28,9 @@ func main() {
}
```

`Scanln` 扫描来自标准输入的文本,将空格分隔的值依次存放到后续的参数内,直到碰到换行。`Scanf` 与其类似,除了 `Scanf` 的第一个参数用作格式字符串,用来决定如何读取。`Sscan` 和以 `Sscan` 开头的函数则是从字符串读取,除此之外,与 `Scanf` 相同。如果这些函数读取到的结果与您预想的不同,您可以检查成功读入数据的个数和返回的错误。
`Scanln()` 扫描来自标准输入的文本,将空格分隔的值依次存放到后续的参数内,直到碰到换行。`Scanf()` 与其类似,除了 `Scanf()` 的第一个参数用作格式字符串,用来决定如何读取。`Sscan...` 和以 `Sscan...` 开头的函数则是从字符串读取,除此之外,与 `Scanf()` 相同。如果这些函数读取到的结果与您预想的不同,您可以检查成功读入数据的个数和返回的错误。

您也可以使用 `bufio` 包提供的缓冲读取(buffered reader来读取数据,正如以下例子所示:
您也可以使用 `bufio` 包提供的缓冲读取器 (buffered reader) 来读取数据,正如以下例子所示:

示例 12.2 [readinput2.go](examples/chapter_12/readinput2.go)

Expand Down Expand Up @@ -60,13 +60,13 @@ func main() {

`bufio.NewReader()` 构造函数的签名为:`func NewReader(rd io.Reader) *Reader`

该函数的实参可以是满足 `io.Reader` 接口的任意对象(任意包含有适当的 `Read()` 方法的对象,请参考[章节11.8](11.8.md)),函数返回一个新的带缓冲的 `io.Reader` 对象,它将从指定读取器(例如 `os.Stdin`)读取内容。
该函数的实参可以是满足 `io.Reader` 接口的任意对象(任意包含有适当的 `Read()` 方法的对象,请参考[章节 11.8](11.8.md)),函数返回一个新的带缓冲的 `io.Reader` 对象,它将从指定读取器(例如 `os.Stdin`)读取内容。

返回的读取器对象提供一个方法 `ReadString(delim byte)`,该方法从输入中读取内容,直到碰到 `delim` 指定的字符,然后将读取到的内容连同 `delim` 字符一起放到缓冲区。

`ReadString` 返回读取到的字符串,如果碰到错误则返回 `nil`。如果它一直读到文件结束,则返回读取到的字符串和 `io.EOF`。如果读取过程中没有碰到 `delim` 字符,将返回错误 `err != nil`

在上面的例子中,我们会读取键盘输入,直到回车键(\n)被按下。
在上面的例子中,我们会读取键盘输入,直到回车键 (`\n`) 被按下。

屏幕是标准输出 `os.Stdout``os.Stderr` 用于显示错误信息,大多数情况下等同于 `os.Stdout`

Expand Down Expand Up @@ -133,15 +133,15 @@ func main() {
**练习 12.1:** [word_letter_count.go](exercises/chapter_12/word_letter_count.go)

编写一个程序,从键盘读取输入。当用户输入 'S' 的时候表示输入结束,这时程序输出 3 个数字:
i) 输入的字符的个数,包括空格,但不包括 '\r' 和 '\n'
i) 输入的字符的个数,包括空格,但不包括 `'\r'``'\n'`
ii) 输入的单词的个数
iii) 输入的行数

**练习 12.2:** [calculator.go](exercises/chapter_12/calculator.go)

编写一个简单的逆波兰式计算器,它接受用户输入的整型数(最大值 999999)和运算符 +、-、\*、/。
输入的格式为:number1 ENTER number2 ENTER operator ENTER --> 显示结果
当用户输入字符 'q' 时,程序结束。请使用您在练习11.13中开发的 `stack` 包。
输入的格式为:`number1 ENTER number2 ENTER operator ENTER --> 显示结果`
当用户输入字符 `'q'` 时,程序结束。请使用您在[练习 11.13](11.12.md) 中开发的 `stack` 包。

## 链接

Expand Down
10 changes: 5 additions & 5 deletions eBook/12.10.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# 12.10 XML 数据格式

下面是与 12.9 节 JSON 例子等价的 XML 版本:
下面是与 [12.9 节](12.9.md) JSON 例子等价的 XML 版本:

```xml
<Person>
Expand All @@ -9,11 +9,11 @@
</Person>
```

如同 json 包一样,也有 `xml.Marshal()``xml.Unmarshal()` 从 XML 中编码和解码数据;但这个更通用,可以从文件中读取和写入(或者任何实现了 io.Reader 和 io.Writer 接口的类型)
如同 `json` 包一样,也有 `xml.Marshal()``xml.Unmarshal()` 从 XML 中编码和解码数据;但这个更通用,可以从文件中读取和写入(或者任何实现了 `io.Reader``io.Writer` 接口的类型)

和 JSON 的方式一样,XML 数据可以序列化为结构,或者从结构反序列化为 XML 数据;这些可以在例子 15.8([twitter_status.go](examples/chapter_15/twitter_status.go))中看到。

encoding/xml 包实现了一个简单的 XML 解析器(SAX),用来解析 XML 数据内容。下面的例子说明如何使用解析器:
`encoding`/`xml` 包实现了一个简单的 XML 解析器(SAX),用来解析 XML 数据内容。下面的例子说明如何使用解析器:

示例 12.17 [xml.go](examples/chapter_12/xml.go)

Expand Down Expand Up @@ -74,9 +74,9 @@ End of token

包中定义了若干 XML 标签类型:StartElement,Chardata(这是从开始标签到结束标签之间的实际文本),EndElement,Comment,Directive 或 ProcInst。

包中同样定义了一个结构解析器:`NewParser` 方法持有一个 io.Reader(这里具体类型是 strings.NewReader)并生成一个解析器类型的对象。还有一个 `Token()` 方法返回输入流里的下一个 XML token。在输入流的结尾处,会返回nilio.EOF
包中同样定义了一个结构解析器:`NewParser()` 方法持有一个 `io.Reader`(这里具体类型是 `strings.NewReader`)并生成一个解析器类型的对象。还有一个 `Token()` 方法返回输入流里的下一个 XML token。在输入流的结尾处,会返回 (`nil`,`io.EOF`)

XML 文本被循环处理直到 `Token()` 返回一个错误,因为已经到达文件尾部,再没有内容可供处理了。通过一个 type-switch 可以根据一些 XML 标签进一步处理。Chardata 中的内容只是一个 []byte,通过字符串转换让其变得可读性强一些。
XML 文本被循环处理直到 `Token()` 返回一个错误,因为已经到达文件尾部,再没有内容可供处理了。通过一个 type-switch 可以根据一些 XML 标签进一步处理。Chardata 中的内容只是一个 `[]byte`,通过字符串转换让其变得可读性强一些。

## 链接

Expand Down
4 changes: 2 additions & 2 deletions eBook/12.11.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

Gob 是 Go 自己的以二进制形式序列化和反序列化程序数据的格式;可以在 `encoding` 包中找到。这种格式的数据简称为 Gob (即 Go binary 的缩写)。类似于 Python 的 "pickle" 和 Java 的 "Serialization"。

Gob 通常用于远程方法调用(RPCs,参见 [15.9节](15.9.md)rpc 包)参数和结果的传输,以及应用程序和机器之间的数据传输。
Gob 通常用于远程方法调用(RPCs,参见 [15.9 节](15.9.md)`rpc` 包)参数和结果的传输,以及应用程序和机器之间的数据传输。
它和 JSON 或 XML 有什么不同呢?Gob 特定地用于纯 Go 的环境中,例如,两个用 Go 写的服务之间的通信。这样的话服务可以被实现得更加高效和优化。
Gob 不是可外部定义,语言无关的编码方式。因此它的首选格式是二进制,而不是像 JSON 和 XML 那样的文本格式。
Gob 并不是一种不同于 Go 的语言,而是在编码和解码过程中用到了 Go 的反射。
Expand All @@ -25,7 +25,7 @@ type U struct { X, Y *int8 }
var u U
```

在接收者中,X 的值是7,Y 的值是0(Y的值并没有从 t 中传递过来,因为它是零值)
在接收者中,`X` 的值是 `7``Y` 的值是 `0``Y` 的值并没有从 `t` 中传递过来,因为它是零值)


和 JSON 的使用方式一样,Gob 使用通用的 `io.Writer` 接口,通过 `NewEncoder()` 函数创建 `Encoder` 对象并调用 `Encode()`;相反的过程使用通用的 `io.Reader` 接口,通过 `NewDecoder()` 函数创建 `Decoder` 对象并调用 `Decode()`
Expand Down
2 changes: 1 addition & 1 deletion eBook/12.12.md
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ type Hash interface {
}
```

通过 io.WriteString 或 hasher.Write 将给定的 []byte 附加到当前的 `hash.Hash` 对象中。
通过 `io.WriteString``hasher.Write` 将给定的 `[]byte` 附加到当前的 `hash.Hash` 对象中。

**练习 12.9**[hash_md5.go](exercises/chapter_12/hash_md5.go)

Expand Down
Loading

0 comments on commit d296444

Please sign in to comment.