当前位置: 首页 > article >正文

GO系列-IO 文件操作

os io

判断文件是否存在

func fileExist(filePath string) (bool, error) {
    _, err := os.Stat(filePath)
    if err == nil {
       return true, nil
    }

    if os.IsNotExist(err) {
       return false, nil
    }
    return false, &CheckFileExistError{filePath}
}

读取文件内容

func readFileContext(file *os.File) (string, error) {
    if file == nil {
       return "", nil
    }

    var buf [1024]byte
    var content []byte
    for {
       n, err := file.Read(buf[:])
       if err == io.EOF {
          //结尾
          break
       } else if err != nil {
          log.Println("Read file error", file.Name())
          return "", err
       }

       content = append(content, buf[:n]...)
    }
    return string(content), nil
}

创建文件&写入文件内容

// 如果不存在 则创建
if !exist {
    log.Println("create file:", filePath)
    newFile, err := os.Create(filePath)
    if err != nil {
       log.Panicln(err.Error())
    }
    // 写入文件
    newFile.WriteString("Hello word !!!\n")
    newFile.Write([]byte("happy every day\n"))
    newFile.Close()
}

打开文件

// 打开这个文件
file1, err := os.Open(filePath)
if err != nil {
    log.Panicln(err.Error())
}

关闭和删除文件

// 删除前关闭文件,否则报错
file1.Close()

// 删除文件
stat1, _ := file1.Stat()
if stat1 != nil {
    log.Println("file is not closed")
}
err = os.Remove(filePath)
if err != nil {
    log.Println("remove file error", filePath, err.Error())
}
log.Println("remove file success", filePath)

copy文件

func copyFile(filePath1 string, filePath2 string) error {
    exist, err := fileExist(filePath1)
    if err != nil {
       return err
    }

    if !exist {
       log.Println("file1 must exist ")
       return nil
    }

    file1, err := os.Open(filePath1)
    if err != nil {
       log.Println("open file1 error")
       return err
    }
    defer file1.Close()

    // 如果存在则删除
    exist, err = fileExist(filePath2)
    if err != nil {
       return err
    }
    if exist {
       os.Remove(filePath2)
    }

    file2, err := os.Create(filePath2)
    if err != nil {
       log.Println("create file2 error")
       return err
    }
    defer file2.Close()

    var buffer [1024]byte
    for {
       n, err := file1.Read(buffer[:])
       if err == io.EOF {
          log.Println("copy complete")
          break
       }
       if err != nil {
          log.Println("copy error")
          return err
       }
       file2.Write(buffer[:n])
    }

    return nil
}

综合示例

package main

import (
    "io"
    "log"
    "os"
)

type CheckFileExistError struct {
    FilePath string
}

func (err CheckFileExistError) Error() string {
    return "Check File[" + err.FilePath + "] Exist Error"
}

func fileExist(filePath string) (bool, error) {
    _, err := os.Stat(filePath)
    if err == nil {
       return true, nil
    }

    if os.IsNotExist(err) {
       return false, nil
    }
    return false, &CheckFileExistError{filePath}
}

func readFileContext(file *os.File) (string, error) {
    if file == nil {
       return "", nil
    }

    var buf [1024]byte
    var content []byte
    for {
       n, err := file.Read(buf[:])
       if err == io.EOF {
          //结尾
          break
       } else if err != nil {
          log.Println("Read file error", file.Name())
          return "", err
       }

       content = append(content, buf[:n]...)
    }
    return string(content), nil
}

func copyFile(filePath1 string, filePath2 string) error {
    exist, err := fileExist(filePath1)
    if err != nil {
       return err
    }

    if !exist {
       log.Println("file1 must exist ")
       return nil
    }

    file1, err := os.Open(filePath1)
    if err != nil {
       log.Println("open file1 error")
       return err
    }
    defer file1.Close()

    // 如果存在则删除
    exist, err = fileExist(filePath2)
    if err != nil {
       return err
    }
    if exist {
       os.Remove(filePath2)
    }

    file2, err := os.Create(filePath2)
    if err != nil {
       log.Println("create file2 error")
       return err
    }
    defer file2.Close()

    var buffer [1024]byte
    for {
       n, err := file1.Read(buffer[:])
       if err == io.EOF {
          log.Println("copy complete")
          break
       }
       if err != nil {
          log.Println("copy error")
          return err
       }
       file2.Write(buffer[:n])
    }

    return nil
}

func main() {
    log.Println("main ...")

    filePath := "./test.txt"
    filePath2 := "./test2.txt"

    exist, err := fileExist(filePath)
    log.Println("file ", filePath, "exist:", exist)
    if err != nil {
       log.Println(err.Error())
    }

    // 如果不存在 则创建
    if !exist {
       log.Println("create file:", filePath)
       newFile, err := os.Create(filePath)
       if err != nil {
          log.Panicln(err.Error())
       }
       // 写入文件
       newFile.WriteString("Hello word !!!\n")
       newFile.Write([]byte("happy every day\n"))
       newFile.Close()
    }

    // 打开这个文件
    file1, err := os.Open(filePath)
    if err != nil {
       log.Panicln(err.Error())
    }

    // 读取文件原始内容
    context, err := readFileContext(file1)
    if err != nil {
       log.Panicln(err.Error())
    }
    log.Println("context:", context)

    // 删除前关闭文件,否则报错
    file1.Close()

    // copy文件
    copyFile(filePath, filePath2)

    // 删除文件
    stat1, _ := file1.Stat()
    if stat1 != nil {
       log.Println("file is not closed")
    }
    err = os.Remove(filePath)
    if err != nil {
       log.Println("remove file error", filePath, err.Error())
    }
    log.Println("remove file success", filePath)

    log.Println("success ..")
}

bufio

bufio包实现了带缓冲区的读写,是对文件读写的封装

bufio缓冲写数据

模式       含义

os.O_WRONLY     只写

os.O_CREATE      创建文件

os.O_RDONLY      只读

os.O_RDWR   读写

os.O_TRUNC 清空

os.O_APPEND      追加

package main

import (
    "bufio"
    "io"
    "log"
    "os"
)

// 写文件
func write(filePath string) {
    // 参数2:打开模式,所有模式d都在上面
    // 参数3是权限控制
    // w写 r读 x执行   w  2   r  4   x  1
    file, err := os.OpenFile(filePath, os.O_CREATE|os.O_WRONLY, 0666)
    if err != nil {
       return
    }
    defer file.Close()
    // 获取writer对象
    writer := bufio.NewWriter(file)
    for i := 0; i < 10; i++ {
       writer.WriteString("hello\n")
    }
    // 刷新缓冲区,强制写出
    writer.Flush()
}

// 读取文件
func read(filePath string) string {
    file, err := os.Open(filePath)
    if err != nil {
       return ""
    }
    defer file.Close()
    var content []byte
    reader := bufio.NewReader(file)
    for {
       line, _, err := reader.ReadLine()
       if err == io.EOF {
          break
       }
       if err != nil {
          return ""
       }
       content = append(content, []byte(string(line)+"\n")...)
    }
    return string(content)
}

func main() {
    log.Println("main ...")

    filePath := "./test1.txt"
    write(filePath)
    content := read(filePath)
    log.Println(content)

    log.Println("success ..")
}

ioutil

package main

import (
    "io/ioutil"
    "log"
)

func main() {
    log.Println("main ...")

    filePath := "./test1.txt"
    // 写文件
    err := ioutil.WriteFile(filePath, []byte("hello word"), 0666)
    if err != nil {
       log.Println(err)
       return
    }

    // 读取文件
    content, err := ioutil.ReadFile(filePath)
    if err != nil {
       log.Println(err)
       return
    }
    log.Println(string(content))

    log.Println("success ..")
}

控制台输入输出

终端其实是一个文件,相关实例如下:

os.Stdin:标准输入的文件实例,类型为*File

os.Stdout:标准输出的文件实例,类型为*File

os.Stderr:标准错误输出的文件实例,类型为*File

以文件的方式操作终端:

package main

import (
    "log"
    "os"
)

func main() {
    log.Println("main ...")

    var buf [16]byte
    // 从控制台读取一行数据
    os.Stdin.Read(buf[:])
    log.Println("read context:", string(buf[:]))

    // 写入到控制台
    os.Stdout.WriteString("hello word\n")

    log.Println("success ..")
}


http://www.kler.cn/a/558280.html

相关文章:

  • wordpress adrotate插件 文件上传漏洞
  • 最新版本Exoplayer扩展FFmpeg音频软解码保姆级教程
  • 23种设计模式之《桥接模式(Bridge)》在c#中的应用及理解
  • SpringBoot3使用RestTemplate请求接口忽略SSL证书
  • 蓝桥备赛(一)- C++入门(上)
  • Unity贴图与模型相关知识
  • PostgreSQL‘会用‘到‘精通‘,学习感悟
  • 《论云上自动化运维及其应用》审题技巧 - 系统架构设计师
  • [原创](Modern C++)现代C++的关键性概念: std::span, 低内存开销的方式来操作大数据.
  • C语言--正序、逆序输出为奇数的位。
  • Spring Boot:开启快速开发新时代
  • 23种设计模式之《组合模式(Composite)》在c#中的应用及理解
  • ETL工具: Kettle入门(示例从oracle到oracle的数据导入)
  • 51单片机学习——动态数码管显示
  • ROS2 应用:按键控制 MoveIt2 中 Panda 机械臂关节位置
  • SAP 代码扫描工具
  • 鹰角基于 Flink + Paimon + Trino 构建湖仓一体化平台实践项目
  • Linux离线环境安装miniconda并导入依赖包
  • Spring 依赖注入实战指南:XML、注解、Java 配置全面对比
  • 备忘录模式:快速恢复原始数据