【Go语言】Golang获取文件大小<优化篇>

昨天写的代码在给导师做测试的时候出现了一些问题,主要有三个:第一,在shell 环境下运行的时候文件路径需要作为参数传递进去;第二,没有做缓存,导致整个程序运行起来很慢;第三,用到的是Golang官方包中提供的一些函数,有很大局限性,在linux下面跑的时候一些特定的路径解析不了。于是今天一天都在改代码。

下面改好的代码实现了以上三点。带参数运行这个很简单,没有什么技术含量的。缓存做了很久,基本思路是去判断给的路径是不是已经运行过了,如果没有,则去调用相关处理函数去读取这个文件夹/文件的大小,并将结果存在一个文件当中,同时记下当前的时间;如果已经读取过了,那么就打开文件,去看看这个时间有没有过期,如果前后时间相差不到60秒的话就将上次的结果返回,如果时间超过了60秒那么就重新读取一次,然后把新的时间和数据记到文件中,这个就是cache 了。还有就是特定的目录解析不了的问题,没有办法,只能去用golang调用shell ,因为Go本身解决的方法很难很难。

 

var file_path string    //路径
var sum_size int64 = 0 //总大小
var dir_name string = “file_size_cache”    //缓存文件目录

//获取单个文件的大小
func getSize(path string) int64 {
fileInfo, err := os.Stat(path)
if err != nil {
panic(err)

}
fileSize := fileInfo.Size() //获取size
return fileSize
}

//执行shell
func system(c string, o …string) {

cmd := exec.Command(c, o…)
var out bytes.Buffer
cmd.Stdout = &out
err := cmd.Run()
data := strings.Fields(out.String())
fmt.Println(data[0])
size, err := strconv.ParseInt(data[0], 10, 64)
sum_size = size
if err != nil {

}
}

//建立缓存文件夹
func mkDir(c string, o … string) {

cmd := exec.Command(c, o…)

err := cmd.Run()
if err != nil {
}

}

//设置缓存
func setCache(path string, size int64) {
content := md(path)
cacheFile, err := os.Create(content)
if err != nil {
fmt.Println(“cache创建失败”, err)
}

strLen, err := cacheFile.WriteString(strconv.Itoa(int(time.Now().Unix())) + “n” + strconv.Itoa(int(size)) + “n”)
if strLen == len(path) {
// fmt.Println(“cache创建成功!”, path, “已经写入”)

//将cache文件转移到缓存文件夹中
cmd:=”mv”

str:=[]string{content,dir_name}

mkDir(cmd,str…)
}

//加密,每一个路径用一个MD5函数处理以后当做cache文件名
func md(path string) string {
content := md5.New()
by := []byte(path)
content.Write(by)
result := hex.EncodeToString(content.Sum(nil))
return result
}

//读取缓存
func getCache(path string) (bool, int64) {
file_name := md(path)
f_pa:=dir_name+”/”+file_name
cacheFile, err := os.Open(f_pa)
if err != nil {

return false, -1
}
defer cacheFile.Close()
inputread := bufio.NewReader(cacheFile)
var data []string
for {
input, ferr := inputread.ReadString(‘n’)
if ferr == io.EOF {
break
}
data = append(data, strings.TrimSpace(input))
}

timeLast, err := strconv.ParseInt(data[0], 10, 64)

if time.Now().Unix()-timeLast < 60 {
rel, err := strconv.ParseInt(data[1], 10, 64)
if err != nil {
}
fmt.Println(data[1])
return true, rel
} else {
return false, 0
}

}

func main() {
cmd := “mkdir”
dir_n:=[]string{dir_name}
mkDir(cmd, dir_n…)

file_path = os.Args[1]

isTrue, num := getCache(file_path)
if isTrue {
sum_size = num
} else {
//以下是golang调用shell
cmd := “du”
str := []string{“-bs”, file_path}
system(cmd, str…)
setCache(file_path, sum_size)
}

}

运行的时候  go run xxx.go 路径

应该是解决了。今天周四了,上班过得好快啊,一周又要结束了。

刘凯宁@C2P
20140717

Share

发表评论

电子邮件地址不会被公开。 必填项已用 * 标注

*


*

您可以使用这些 HTML 标签和属性: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>