《Go Web编程实战派——从入门到精通》学习笔记之第6章 文件处理
第6章 文件处理
6.1 操作目录与文件
6.1.1 操作目录
import (
os
path
)
- 创建目录
//func Mkdir(name string, perm FileMode) error
package main
import (
"fmt"
"os"
)
func main() {
//创建一个名为“test”的目录,perm权限为0777
err := os.Mkdir("test", 0777)
if err != nil {
fmt.Println(err)
}
}
//func MkdirAll(path string, perm FileMode) error
package main
import (
"fmt"
"os"
)
func main() {
//根据path创建多级子目录,例如dir1/dir2/dir3
err :=os.MkdirAll("dir1/dir2/dir3", 0777)
if err != nil {
fmt.Println(err)
}
}
package main
import (
"fmt"
"os"
"time"
)
func main() {
uploadDir := "static/upload/" + time.Now().Format("2006/01/02/")
err := os.MkdirAll(uploadDir , 777)
if err!=nil{
fmt.Println(err)
}
}
- 重命名目录
//func Rename(oldpath, newpath string) error
package main
import (
"fmt"
"log"
"os"
)
func main() {
//创建一个名为“dir_name1”的目录,perm权限为0777
err := os.Mkdir("dir_name1", 0777)
if err != nil {
fmt.Println(err)
}
oldName := "dir_name1"
newName := "dir_name2"
//将dir_name1重命名为dir_name2
err = os.Rename(oldName, newName)
if err != nil {
log.Fatal(err)
}
}
- 删除目录
//func Remove(name string) error
//非空目录出错
package main
import (
"log"
"os"
)
func main() {
err := os.Remove("dir1")
if err != nil {
log.Fatal(err)
}
}
//func RemoveAll(name string) error
package main
import (
"log"
"os"
)
func main() {
//先创建多级子目录
os.MkdirAll("test1/test2/test3", 0777)
//删除test1目录及其子目录
err := os.RemoveAll("test1")
if err != nil {
log.Fatal(err)
}
}
- 遍历目录
//func Walk(root string, walkFn WalkFunc) error
package main
import (
"fmt"
"os"
"path/filepath"
)
func scan(path string, f os.FileInfo, err error) error {
fmt.Printf("Scaned: %s\n", path)
return nil
}
func main() {
//根据path创建多级子目录,例如dir1/dir2/dir3
err :=os.MkdirAll("test_walk/dir2/dir3", 0777)
if err != nil {
fmt.Println(err)
}
root := `./test_walk`
err = filepath.Walk(root, scan)
fmt.Printf("filepath.Walk() returned %v\n", err)
}
6.1.2 创建文件
//func Create(name string) (*File, error)
package main
import (
"fmt"
"os"
)
func main() {
// 创建文件
//文件的创建,Create会根据传入的文件名创建文件,默认权限是0666
fp, err := os.Create("./demo.txt") // 如果文件已存在,会将文件清空。
fmt.Println(fp, err) // &{0xc000054180} <nil>
fmt.Printf("%T", fp) // *os.File 文件指针类型
if err != nil {
fmt.Println("文件创建失败。")
//创建文件失败的原因有:
//1、路径不存在 2、权限不足 3、打开文件数量超过上限 4、磁盘空间不足等
return
}
// defer延迟调用
defer fp.Close() //关闭文件,释放资源。
}
6.1.3 打开与关闭文件
//func Open(name string) (file *File, err Error)
//func (f *File) Close() error
package main
import (
"fmt"
"os"
)
func main() {
// 打开文件
file, err := os.Open("open.txt")
if err != nil {
fmt.Printf("打开文件出错:%v\n", err)
}
fmt.Println(file)
// 关闭文件
err = file.Close()
if err != nil {
fmt.Printf("关闭文件出错:%v\n", err)
}
}
//func OpenFile(name string, flag int, perm uint32) (file *File, err Error)
package main
import (
"fmt"
"os"
)
func main() {
// 读写方式打开文件
fp, err := os.OpenFile("./open.txt", os.O_CREATE|os.O_APPEND, 0666)
if err != nil {
fmt.Println("文件打开失败。")
return
}
// defer延迟调用
defer fp.Close() //关闭文件,释放资源。
}
6.1.4 读写文件
- 读文件
//带缓冲方式读
//func NewReader(rd io.Reader) *Reader
package main
import (
"bufio"
"fmt"
"io"
"os"
)
func main() {
// 打开文件
file, err := os.Open("read.txt")
if err != nil {
fmt.Printf("打开文件出错:%v\n", err)
}
// 及时关闭文件句柄
defer file.Close()
// bufio.NewReader(rd io.Reader) *Reader
reader := bufio.NewReader(file)
// 循环读取文件的内容
for {
line, err := reader.ReadString('\n') // 读到一个换行符就结束
if err == io.EOF { // io.EOF表示文件的末尾
break
}
// 输出内容
fmt.Print(line)
}
}
//直接读到内存
//func ReadFile(filename string)([]byte, error)
package main
import (
"fmt"
"io/ioutil"
)
func main() {
// 使用 io/ioutil.ReadFile 方法一次性将文件读取到内存中
filePath := "read2.txt"
content, err := ioutil.ReadFile(filePath)
if err != nil {
// log.Fatal(err)
fmt.Printf("读取文件出错:%v", err)
}
fmt.Printf("%v\n", content)
fmt.Printf("%v\n", string(content))
}
- 写文件
//func (file *File) Write(b []byte) (n int, err Error)
package main
import (
"fmt"
"os"
)
func main() {
file, err := os.OpenFile("write1.txt", os.O_CREATE|os.O_RDWR, 0666)
if err != nil {
fmt.Println(err)
}
defer file.Close()
content := []byte("你好世界!")
if _, err = file.Write(content); err != nil {
fmt.Println(err)
}
fmt.Println("写入成功!")
}
//func (file *File) WriteAt(b []byte, off int64) (n int, err Error)
package main
import (
"fmt"
"os"
)
func main() {
file, err := os.Create("writeAt.txt")
if err != nil {
panic(err)
}
defer file.Close()
file.WriteString("Go Web编程实战派从入门到精通")
n, err := file.WriteAt([]byte("Go语言Web"), 24)
if err != nil {
panic(err)
}
fmt.Println(n)
}
//func (file *File) WriteString(s string) (ret int, err Error)
package main
import (
"os"
)
func main() {
file, err := os.Create("WriteString.txt")
if err != nil {
panic(err)
}
defer file.Close()
file.WriteString("Go Web编程实战派从入门到精通")
}
/*
func (file *File) WriteString(s string) (ret int, err Error) {
return f.Write([]byte(s))
}
*/
package main
import (
"fmt"
"os"
)
func main() {
//新建文件
fout, err := os.Create("./write4.txt")
if err != nil {
fmt.Println(err)
return
}
defer fout.Close()
for i := 0; i < 5; i++ {
outstr := fmt.Sprintf("%s:%d\r\n", "Hello Go", i) //Sprintf格式化
// 写入文件
fout.WriteString(outstr) //string信息
fout.Write([]byte("i love go\r\n")) //byte类型
}
}
6.1.5 移动和重命名文件
//func Rename(oldpath, newpath string) error
package main
import (
"fmt"
"os"
)
func main() {
//创建一个名为“test_rename.txt”的空文件
_, err := os.Create("./test_rename.txt") // 如果文件已存在,会将文件清空。
if err != nil {
fmt.Println(err)
}
//创建一个名为“test_rename”的目录,perm权限为0777
err = os.Mkdir("test_rename", 0777)
//将test_rename.txt移动到test_rename目录,并将名字重命名为test_rename_new.txt
err = os.Rename("./test_rename.txt", "./test_rename/test_rename_new.txt")
if err != nil {
fmt.Println(err)
return
}
}
6.1.6 删除文件
//func Remove(name string) error
//func RemoveAll(name string) error
package main
import (
"fmt"
"os"
)
func main() {
//创建一个名为“test_rename”的目录,perm权限为0777
err := os.Mkdir("test_remove", 0777)
if err != nil {
fmt.Println(err)
}
fmt.Println("created dir:test_remove")
//创建一个名为“test_remove1.txt”的空文件
_, err = os.Create("./test_remove/test_remove1.txt") // 如果文件已存在,会将文件清空。
if err != nil {
fmt.Println(err)
}
fmt.Println("created file:test_remove1.txt")
_, err = os.Create("./test_remove/test_remove2.txt")
if err != nil {
fmt.Println(err)
}
fmt.Println("created file:test_remove2.txt")
_, err = os.Create("./test_remove/test_remove3.txt")
if err != nil {
fmt.Println(err)
}
fmt.Println("created file:test_remove3.txt")
err = os.Remove("./test_remove/test_remove1.txt")
if err != nil {
fmt.Printf("removed ./test_remove/test_remove1.txt err : %v\n", err)
}
fmt.Println("removed file:./test_remove/test_remove1.txt")
err = os.RemoveAll("./test_remove")
if err != nil {
fmt.Printf("remove all ./test_remove err : %v\n", err)
}
fmt.Println("removed all files:./test_remove")
}
6.1.7 复制文件
//func Copy(dst Writer, src Reader) (written int64, err error)
package main
import (
"fmt"
"io"
"os"
)
func main() {
//先创建一个名为:test_copy1.zip文件
_, err := os.Create("./test_copy1.zip") // 如果文件已存在,会将文件清空。
if err != nil {
fmt.Println(err)
}
//打开文件test_copy1.zip,获取文件指针
srcFile, err := os.Open("./test_copy1.zip")
if err != nil {
fmt.Printf("open file err = %v\n", err)
return
}
defer srcFile.Close()
//打开文件要复制的新文件名test_copy2.zip,获取文件指针
dstFile, err := os.OpenFile("./test_copy2.zip", os.O_WRONLY|os.O_CREATE, 0755)
if err != nil {
fmt.Printf("open file err = %v\n", err)
return
}
defer dstFile.Close()
//通过Copy方法
result, err := io.Copy(dstFile, srcFile)
if err == nil {
fmt.Println("复制成功,复制的字节数为: ", result)
}
}
package main
import (
"fmt"
"io"
"log"
"os"
)
//自定义复制方法
func DoCopy(srcFileName string, dstFileName string) {
//打开源文件
srcFile, err := os.Open(srcFileName)
if err != nil {
log.Fatalf("源文件读取失败,err:%v\n", err)
}
defer func() {
err = srcFile.Close()
if err != nil {
log.Fatalf("源文件关闭失败,err:%v\n", err)
}
}()
//创建目标文件,稍后会向这个目标文件写入拷贝内容
distFile, err := os.Create(dstFileName)
if err != nil {
log.Fatalf("目标文件创建失败,err:%v\n", err)
}
defer func() {
err = distFile.Close()
if err != nil {
log.Fatalf("目标文件关闭失败,err:%v\n", err)
}
}()
//定义指定长度的字节切片,每次最多读取指定长度
var tmp = make([]byte, 1024*4)
//循环读取并写入
for {
n, err := srcFile.Read(tmp)
n, _ = distFile.Write(tmp[:n])
if err != nil {
if err == io.EOF {
return
} else {
log.Fatalf("拷贝过程中发生错误,错误err:%v\n", err)
}
}
}
}
func main() {
//先创建一个.zip文件
_, err := os.Create("./test.zip") // 如果文件已存在,会将文件清空。
if err != nil {
fmt.Println(err)
}
//复制一个名为test2.zip的文件
DoCopy("./test.zip", "./test2.zip")
}
6.1.9 文件链接
//硬链接
//func Link(oldname, newname string) error
package main
import (
"fmt"
"os"
)
func main() {
// 创建文件
//文件的创建,Create会根据传入的文件名创建文件,默认权限是0666//-rw-r--r--
fp, err := os.Create("./link1.txt") // 如果文件已存在,会将文件清空。
// defer延迟调用
defer fp.Close() //关闭文件,释放资源。
if err != nil {
fmt.Println("文件创建失败。")
}
err = os.Link("link1.txt", "link2.txt")
if err != nil {
fmt.Println("err:", err)
}
}
//软链接
//func SymLink(oldname, newname string) error
package main
import (
"fmt"
"os"
)
func main() {
// 创建文件
//文件的创建,Create会根据传入的文件名创建文件,默认权限是0666//-rw-r--r--
fp, err := os.Create("./link2.txt") // 如果文件已存在,会将文件清空。
// defer延迟调用
defer fp.Close() //关闭文件,释放资源。
if err != nil {
fmt.Println("文件创建失败。")
}
err = os.Symlink("link2.txt", "link3.txt")
if err != nil {
fmt.Println("err:", err)
}
}
6.2 处理XML文件
XML(eXtensible Markup Language,可扩展标记语言)
6.2.1 解析XML文件
//func Unmarshal(data []byte, v interface{}) error
Go解析XML原则:
- 结构体
<!--email_config.xml-->
<?xml version="1.0" encoding="UTF-8"?>
<config>
<smtpServer>smtp.163.com</smtpServer>
<smtpPort>25</smtpPort>
<sender>test@163.com</sender>
<senderPassword>123456</senderPassword>
<receivers flag="true">
<user>shirdonliao@gmail.com</user>
<user>test99999@qq.com</user>
</receivers>
</config>
package main
import (
"encoding/xml"
"fmt"
"io/ioutil"
"os"
)
type EmailConfig struct {
XMLName xml.Name `xml:"config"`
SmtpServer string `xml:"smtpServer"`
SmtpPort int `xml:"smtpPort"`
Sender string `xml:"sender"`
SenderPassword string `xml:"senderPassword"`
Receivers EmailReceivers `xml:"receivers"`
}
type EmailReceivers struct {
Flag string `xml:"flag,attr"`
User []string `xml:"user"`
}
func main() {
file, err := os.Open("email_config.xml")
if err != nil {
fmt.Printf("error: %v", err)
return
}
defer file.Close()
data, err := ioutil.ReadAll(file)
if err != nil {
fmt.Printf("error: %v", err)
return
}
v := EmailConfig{}
err = xml.Unmarshal(data, &v)
if err != nil {
fmt.Printf("error: %v", err)
return
}
fmt.Println(v)
fmt.Println("SmtpServer is : ",v.SmtpServer)
fmt.Println("SmtpPort is : ",v.SmtpPort)
fmt.Println("Sender is : ",v.Sender)
fmt.Println("SenderPasswd is : ",v.SenderPassword)
fmt.Println("Receivers.Flag is : ",v.Receivers.Flag)
for i,element := range v.Receivers.User {
fmt.Println(i,element)
}
}
:输出
{{ config} smtp.163.com 25 test@163.com 123456 {true [shirdonliao@gmail.com test99999@qq.com]}}
SmtpServer is : smtp.163.com
SmtpPort is : 25
Sender is : test@163.com
SenderPasswd is : 123456
Receivers.Flag is : true
0 shirdonliao@gmail.com
1 test99999@qq.com
6.2.2 生成XML文件
//func Marshal(v interface{}) ([]byte, error)
//增加前缀和缩进
//func MarshalIndent(v interface{}, prefix, indent string) ([]byte, error)
package main
import (
"encoding/xml"
"fmt"
"os"
)
type Languages struct {
XMLName xml.Name `xml:"languages"`
Version string `xml:"version,attr`
Lang []Language `xml:"language"`
}
type Language struct {
Name string `xml:"name"`
Site string `xml:"site`
}
func main() {
v := &Languages{Version: "2"}
v.Lang = append(v.Lang, Language{"JAVA", "https://www.java.com/"})
v.Lang = append(v.Lang, Language{"Go", "https://golang.org/"})
output, err := xml.MarshalIndent(v, " ", " ")
if err != nil {
fmt.Printf("error %v", err)
return
}
file, _ := os.Create("languages.xml")
defer file.Close()
file.Write([]byte(xml.Header)) //生成XML头
file.Write(output)
}
<!--languages.xml-->
<?xml version="1.0" encoding="UTF-8"?>
<languages>
<Version>2</Version>
<language>
<name>JAVA</name>
<Site>https://www.java.com/</Site>
</language>
<language>
<name>Go</name>
<Site>https://golang.org/</Site>
</language>
</languages>
6.3 处理JSON文件
JSON(JavaScript Object Notation,JavaScript对象表示法),基于文本,独立于语言的轻量级数据交换格式。键用(“”)括起来,值是任意类型。
{
"id": "888",
"info": {
"name": "jack",
"age": 18
}
}
6.3.1 读取JSON文件
json_parse.json
{
"port": "27017",
"mongo": {
"mongoAddr": "127.0.0.1",
"mongoPoolLimit": 500,
"mongoDb": "my_db",
"mongoCollection": "table1"
}
}
package main
import (
"encoding/json"
"fmt"
"io/ioutil"
)
//定义配置文件解析后的结构
type MongoConfig struct {
MongoAddr string
MongoPoolLimit int
MongoDb string
MongoCollection string
}
type Config struct {
Port string
Mongo MongoConfig
}
func main() {
v := Config{}
err := Load("json_parse.json", &v)
if err != nil {
return
}
fmt.Println(v.Port)
fmt.Println(v.Mongo.MongoDb)
}
func Load(filename string, v interface{}) error {
//ReadFile函数会读取文件的全部内容,并将结果以[]byte类型返回
data, err := ioutil.ReadFile(filename)
if err != nil {
return err
}
//读取的数据为json格式,需要进行解码
err = json.Unmarshal(data, v)
if err != nil {
return err
}
return nil
}
6.3.2 生成JSON文件
package main
import (
"encoding/json"
"fmt"
"os"
)
type User struct {
UserName string
NickName string `json:"nickname"`
Email string
}
func main() {
user := User{
UserName: "Jack",
NickName: "Ma",
Email: "xxxxx@qq.com",
}
//data, err := json.Marshal(&user)
data, err := json.MarshalIndent(&user, "", "\t")
if err != nil {
fmt.Printf("json.Marshal failed,err:", err)
return
}
fmt.Printf("%s\n", string(data))
file, err := os.Create("json_write.json")
if err != nil {
fmt.Printf("os.Create err:", err)
return
}
defer file.Close()
file.Write(data)
}
6.4 处理正则表达式
6.4.1 正则表达式简介
正则表达式特点:
(1)灵活性、逻辑性和功能性非常强。
(2)简单方式实现字符串的复杂控制。
(3)晦涩难懂。
正则表达式提高文本处理能力,用于表单输入验证、文本提取、数据分析等。
正则表达式由普通字符(a~z
、A~Z
、0~9
等)和特殊字符(元字符)组成。
(1)普通字符
普通字符包括大小写字母、数字、标点符号和其他符号。普通字符包括可打印字符和非打印字符(计算机中存在但不能够显示或打印的字符)。
非打印字符 | 描述 |
---|---|
\cx | x指明控制字符,\cM匹配Control+M或回车符。x为[a-zA-Z],否则视为’c’字符。 |
\f | 换页符,等价于\x0c和\cL。 |
\n | 换行符,等价于\x0a和\cJ。 |
\r | 回车符,等价于\x0d和\cM。 |
\s | 任意空白字符(空格、制表符、换页符等),等价于[\r\n\r\t\v]。 |
\S | 任意非空白字符(空格、制表符、换页符等),等价于[^\r\n\r\t\v]。 |
\t | 制表符,等价于\x09和\cl。 |
\v | 垂直制表符,等价于\x0b和\cK。 |
(2)特殊字符
特殊含义的字符。匹配特殊字符,必须转义()。
特殊字符 | 描述 |
---|---|
$ | 字符串结尾,若设置RegExp的Multiline属性,$也匹配"\n"或"\r"。 |
() | 子表达式的开始和结束。 |
* | 零或多。 |
+ | 一或多。 |
. | 除"\n"外任意单字符。 |
[ | 标记中括号表达式的开始。 |
? | 零或一,或指明非贪婪限定符。 |
\ | 将下一个字符标记为特殊字符、原义字符、向后引用、八进制转义符。 |
^ | 字符串开始,方括号表达式中使用表示取反。 |
{ | 标记限定符表达式的开始。 |
| | 选择。 |
(3)限定符
限定给定组件必须出现多少次。
限定符 | 描述 |
---|---|
* | 零或多,等价于{0,}。 |
+ | 一或多,等价于{1,}。 |
? | 零或一,等价于{0,1}。 |
{n} | n。 |
{n,} | 大于等于n。 |
{n,m} | 大于等于n,小于等于m。 |
Chapter [1-9][0-9]*
*、+、?默认贪婪,后面加?实现非贪婪或最小匹配。
<.*>
<.*?>
(4)定位符
定位符 | 描述 |
---|---|
^ | 字符串开始,若设置RegExp的Multiline属性,^也匹配"\n"或"\r"。 |
$ | 字符串结尾,若设置RegExp的Multiline属性,$也匹配"\n"或"\r"。 |
\b | 字边界,即字与空格间的位置。 |
\B | 非字边界。 |
(5)选择
(6)反向引用
(7)运算符优先级
6.4.2 使用Go正则表达式
- regexp包的常用函数
(1)获取正则对象
func Compile(expr string) (*Regexp, error)
func MustCompile(str string) *Regexp
MustCompile()函数失败会宕机。
reg, err := regexp.Compile(`\d+`)
reg := regexp.MustCompile(`\d+`)
(2)匹配检测
func (re *Regexp) MatchString(s string) bool
func (re *Regexp) Match(b []byte) bool
text := "Hello Gopher, Hello Go Web"
reg := regexp.MustCompile(`\w+`)
fmt.Println(reg.MatchString(text))
match, _ := regexp.MatchString("H(.*)d!", "Hello World!")
fmt.Println(match)
match, _ = regexp.Match("H(.*)d!", []byte("Hello World!"))
fmt.Println(match)
r, _ := regexp.Compile("H(.*)d!")
fmt.Println(r.MatchString("Hello World!"))
(3)查找
func (re *Regexp) FindString(s string) string
返回左侧第一个匹配结果。
func (re *Regexp) FindAllString(s string, n int) []string
n限定查找数量,-1不限制。
text := "Hello Gopher, Hello Go Web"
reg := regexp.MustCompile(`\w+`)
fmt.Println(reg.FindAllString(text, -1))
func (re *Regexp) FindAll(b []byte, n int) [][]byte
(4)查找匹配位置
(5)替换
(6)分割
2. regexp包的应用示例
phone.go
package main
import (
"fmt"
"regexp"
)
func main() {
res2 := findPhoneNumber("13688888888")
fmt.Println(res2) // true
res2 = findPhoneNumber("02888888888")
fmt.Println(res2) // false
res2 = findPhoneNumber("123456789")
fmt.Println(res2) // false
}
func findPhoneNumber(str string) bool {
// 创建一个正则表达式匹配规则对象
reg := regexp.MustCompile("^1[1-9]{10}")
// 利用正则表达式匹配规则对象匹配指定字符串
res := reg.FindAllString(str, -1)
if (res == nil) {
return false
}
return true
}
email.go
package main
import (
"fmt"
"regexp"
)
func main() {
res := findEmail("8888@qq.com")
fmt.Println(res) // true
res = findEmail("shir?don@qq.com")
fmt.Println(res) // false
res = findEmail("8888@qqcom")
fmt.Println(res) // false
}
func findEmail(str string) bool {
reg := regexp.MustCompile("^[a-zA-Z0-9_]+@[a-zA-Z0-9]+\\.[a-zA-Z0-9]+")
res := reg.FindAllString(str, -1)
if (res == nil) {
return false
}
return true
}
6.5 处理CSV文件
package main
import (
"encoding/csv"
"fmt"
"os"
)
func main() {
Write_csv()
Read_csv()
}
func Write_csv() {
f, err := os.Create("test.csv")
if err != nil {
fmt.Println(err)
return
}
defer f.Close()
var data = make([][]string, 3)
data[0] = []string{"标题", "作者", "时间"}
data[1] = []string{"羊皮卷", "鲁迅", "2008"}
data[2] = []string{"易筋经", "唐生", "665"}
f.WriteString("\xEF\xBB\xBF") //写入一个UTF-8 BOM
w := csv.NewWriter(f) //创建一个新的写入文件流
w.WriteAll(data)
w.Flush()
}
func Read_csv() {
f, err := os.Open("test.csv")
if err != nil {
fmt.Println(err)
return
}
defer f.Close()
w := csv.NewReader(f)
data, err := w.ReadAll()
if err != nil {
fmt.Println(err)
return
}
fmt.Println(data)
}
6.6 处理日志记录
log包提供3类函数处理日志:
- Print类函数,处理一般日志,退出码0(正常)。
- Panic类函数,处理意外日志,退出码1。
- Fatal类函数,处理致命日志,退出码1。
Print类函数
package main
import (
"log"
)
func main() {
no := []int{6, 8}
log.Print("Print NO. ", no, "\n")
log.Println("Println NO.", no)
log.Printf("Printf NO. with item [%d,%d]\n", no[0], no[1])
}
Panic类函数
package main
import (
"log"
)
func main() {
no := []int{6, 8}
log.Panicln("Println NO.", no)
}
Fatal类函数
package main
import (
"log"
)
func main() {
no := []int{6, 8}
log.Fatalln("Println NO.", no)
}
自定义Logger类型。
func New(out io.Writer, prefix string, flag int) *Logger
- out,输出位置。
- prefix,日志级别。[Info],[Warning]等。
- flags,选项,显示日志开头部分。
package main
import (
"log"
"os"
)
func main() {
fileName := "New.log"
logFile, err := os.Create(fileName)
defer logFile.Close()
if err != nil {
log.Fatalln("open file error")
}
debugLog := log.New(logFile, "[Info]", log.Llongfile)
debugLog.Println("Info Level Message")
debugLog.SetPrefix("[Debug]")
debugLog.Println("Debug Level Message")
}