Go語言學習筆記(十八)之檔案讀寫
阿新 • • 發佈:2019-01-05
25.檔案讀寫
1.檔案開啟和讀
A.檔案分類:文字和二進位制檔案
B.檔案存取方式:隨機存取和順序存取
檔案開啟程式碼示例:
1: package main2:3: import (4: "bufio"5: "fmt"6: "io"7: "os"8: )9:10: func main() {11: //只讀的方式開啟12: inputFile, err := os.Open("input.dat")13: if err != nil {14: fmt.Printf("open file err:%v\n", err)15: return16: }17: defer inputFile.Close()18: }
讀檔案
file.Read和file.ReadAt.
讀到檔案末尾返回:io.EOF
讀出整個檔案程式碼示例
1: package main2:3: import (4: "fmt"5: "io"6: "os"7: )8:9: func main() {10: //只讀的方式開啟11: inputFile, err := os.Open(`D:\project\goland\files\wenjianduxie.go`)12: //如果你檔案在GOPath裡面,可以用下面的路徑13: //inputFile, err := os.Open("./wenjianduxie.go")14: if err != nil {15: fmt.Printf("err=%v\n", err)16: return17: }18: defer func() {19: err := inputFile.Close()20: if err != nil {21: fmt.Println("err1=", err)22: }23: }()24: var buf [128]byte25: var content []byte26: for {27: n, err := inputFile.Read(buf[:])28: if err == io.EOF {29: // 代表檔案讀完了30: break31: }32: if err != nil {33: fmt.Println("err=", err)34: }35: fmt.Println("length:", n)36: // 將一個切片追加到另一個切片37: content = append(content, buf[:n]...)38: fmt.Println("data:\n", string(content))39: }40: }
bufio原理
由於檔案讀寫相對記憶體讀寫效能較差,所以在讀大檔案時需要新增一層緩衝區,這就是bufio。
缺點:可能會丟失快取的資料
1: func main() {2: inputFile, err := os.Open("input.dat")3: if err != nil {4: fmt.Println("err=", err)5: return6: }7:8: defer inputFile.Close()9: inputReader := bufio.NewReader(inputFile)10: for {11: // 以換行符為分隔,一行一行打印出來。12: inputString, readerError :=inputReader.ReadString("\n")13: if readerError == io.EOF {14: return15: }16: fmt.Printf("The input was : %s", inputString)17: }18: }
ioutil直接讀取整個檔案
1: func main() {2: inputFile := "products.txt"3: outputFile := "products_copy.txt"4: buf, err := ioutil.ReadFile(inputFile)5: if err != nil{6: fmt.Fprintf(os.Stderr, "File Error:%s\n", err)7: return8: }9: fmt.Printf("%s\n", string(buf))10: }
讀取gzip壓縮檔案
1: func main() {2: zipfile := "Myfile.gz"3: //open裡面也可以寫路徑4: fi, err1 := os.Open(zipfile)5: if err1 != nil {6: fmt.Fprintf(os.Stderr, "File Error:%s\n", err1)7: os.Exit(1)8: }9: fz, err2 := gzip.NewReader(fi)10: if err2 != nil {11: fmt.Fprintf(os.Stderr,"File Error:%s\n", err2)12: return13: }14: var r *bufio.Reader15: r = bufio.NewReader(fz)16: for {17: line, err := r.ReadString('\n')18: if err != nil {19: fmt.Println(“Done reading file”)20: os.Exit(0)21: }22: fmt.Println(line)23: }24: }
2.檔案寫入
os.OpenFile("檔名",檔案開啟模式,許可權控制)
檔案開啟模式:
1. os.O_WRONLY 只寫
2. os.O_CREATE 建立檔案
3. os.O_RDONLY 只讀
4. os.O_RDWR 讀寫
5. os.O_TRUNC 清空
6. OS.O_APPEND 追加
ps:可以這樣寫: os.O_WRONLY|os.O_CREATE,順序從左到右
許可權控制:
r --> 004
w --> 002
x –> 001
api
1: file.Write()2: file.WriteAt()3: file.WriteString()
bufio檔案寫入快取區
1: writer := bufio.NewWriter() // 開闢快取區2: writer.WriteString() // 寫入快取區3: writer.Flush() // 重新整理,從快取區寫入檔案
ioutil寫入整個檔案
1: inputFile := "舊檔案"2: outputFile := "寫入的新檔案"3: buf, err := ioutil.ReadFile(inputFile)4: err = ioutil.WriteFile(outputFile, buf, 0x644)
3.defer原理圖示
執行順序從上到下
{返回值=x}
return x --
{RET指令}
{返回值=x}
defer原理 -- {執行defer語句}
{RET指令}