12.2.1 读文件
os.Fileos.Stdinos.Stdout*os.File
示例 12.4 fileinput.go:
package main
import (
"bufio"
"fmt"
"io"
"os"
)
func main() {
inputFile, inputError := os.Open("input.dat")
if inputError != nil {
fmt.Printf("An error occurred on opening the inputfile\n" +
"Does the file exist?\n" +
"Have you got acces to it?\n")
return // exit the function on error
}
defer inputFile.Close()
inputReader := bufio.NewReader(inputFile)
for {
inputString, readerError := inputReader.ReadString('\n')
fmt.Printf("The input was: %s", inputString)
if readerError == io.EOF {
return
}
}
}
inputFile*os.FileosOpenstringinput.dat
inputFile, inputError = os.Open("input.dat")defer inputFile.Close()bufio.NewReader
bufio
ReadString('\n')ReadBytes('\n')
ReadStringReadBytesReadLine()
readerErrorio.EOFreturn
其他类似函数:
1) 将整个文件的内容读到一个字符串里:
io/ioutilioutil.ReadFile()[]byteWriteFile()[]byte
package main
import (
"fmt"
"io/ioutil"
"os"
)
func main() {
inputFile := "products.txt"
outputFile := "products_copy.txt"
buf, err := ioutil.ReadFile(inputFile)
if err != nil {
fmt.Fprintf(os.Stderr, "File Error: %s\n", err)
// panic(err.Error())
}
fmt.Printf("%s\n", string(buf))
err = ioutil.WriteFile(outputFile, buf, 0644) // oct, not hex
if err != nil {
panic(err.Error())
}
}
2) 带缓冲的读取
ReadString()bufio.ReaderRead()
buf := make([]byte, 1024)
...
n, err := inputReader.Read(buf)
if (n == 0) { break}
变量 n 的值表示读取到的字节数.
3) 按列读取文件中的数据
fmt
示例 12.6 read_file2.go:
package main
import (
"fmt"
"os"
)
func main() {
file, err := os.Open("products2.txt")
if err != nil {
panic(err)
}
defer file.Close()
var col1, col2, col3 []string
for {
var v1, v2, v3 string
_, err := fmt.Fscanln(file, &v1, &v2, &v3)
// scans until newline
if err != nil {
break
}
col1 = append(col1, v1)
col2 = append(col2, v2)
col3 = append(col3, v3)
}
fmt.Println(col1)
fmt.Println(col2)
fmt.Println(col3)
}
输出结果:
[ABC FUNC GO]
[40 56 45]
[150 280 356]
pathfilepath
import "path/filepath"
filename := filepath.Base(path)
练习 12.3:read_csv.go
文件 products.txt 的内容如下:
"The ABC of Go";25.5;1500
"Functional Programming with Go";56;280
"Go for It";45.9;356
"The Go Way";55;500
每行的第一个字段为 title,第二个字段为 price,第三个字段为 quantity。内容的格式基本与 示例 12.3c 的相同,除了分隔符改成了分号。请读取出文件的内容,创建一个结构用于存取一行的数据,然后使用结构的切片,并把数据打印出来。
encoding/csv
12.2.2 包:读取压缩文件
compress
下面的程序展示了如何读取一个 gzip 文件。
示例 12.7 gzipped.go:
package main
import (
"fmt"
"bufio"
"os"
"compress/gzip"
)
func main() {
fName := "MyFile.gz"
var r *bufio.Reader
fi, err := os.Open(fName)
if err != nil {
fmt.Fprintf(os.Stderr, "%v, Can't open %s: error: %s\n", os.Args[0], fName,
err)
os.Exit(1)
}
fz, err := gzip.NewReader(fi)
if err != nil {
r = bufio.NewReader(fi)
} else {
r = bufio.NewReader(fz)
}
for {
line, err := r.ReadString('\n')
if err != nil {
fmt.Println("Done reading file")
os.Exit(0)
}
fmt.Println(line)
}
}
12.2.3 写文件
请看以下程序:
示例 12.8 fileoutput.go:
package main
import (
"os"
"bufio"
"fmt"
)
func main () {
// var outputWriter *bufio.Writer
// var outputFile *os.File
// var outputError os.Error
// var outputString string
outputFile, outputError := os.OpenFile("output.dat", os.O_WRONLY|os.O_CREATE, 0666)
if outputError != nil {
fmt.Printf("An error occurred with file opening or creation\n")
return
}
defer outputFile.Close()
outputWriter := bufio.NewWriter(outputFile)
outputString := "hello world!\n"
for i:=0; i<10; i++ {
outputWriter.WriteString(outputString)
}
outputWriter.Flush()
}
bufioWriteroutput.dat
outputFile, outputError := os.OpenFile("output.dat", os.O_WRONLY|os.O_CREATE, 0666)
OpenFile
我们通常会用到以下标志:
os.O_RDONLYos.O_WRONLYos.O_CREATEos.O_TRUNC
OpenFile
然后,我们创建一个写入器(缓冲区)对象:
outputWriter := bufio.NewWriter(outputFile)
outputWriter.WriteString(outputString)
outputWriter.Flush()
fmt.Fprintf(outputFile, "Some test data.\n")fmtio.Writer
filewrite.gofmt.FPrintf
示例 12.8 filewrite.go:
package main
import "os"
func main() {
os.Stdout.WriteString("hello, world\n")
f, _ := os.OpenFile("test", os.O_CREATE|os.O_WRONLY, 0666)
defer f.Close()
f.WriteString("hello, world in a file\n")
}
os.Stdout.WriteString("hello, world\n")
f, _ := os.OpenFile("test", os.O_CREATE|os.O_WRONLY, 0666)
f.WriteString( )
练习 12.4:wiki_part1.go
(这是一个独立的练习,但是同时也是为章节15.4做准备)
程序中的数据结构如下,是一个包含以下字段的结构:
type Page struct {
Title string
Body []byte
}
save
load*Pageioutil