为了账号安全,请及时绑定邮箱和手机立即绑定

为什么 Logger.Output 在检查 Lshortfile/Llongfile 标志之

为什么 Logger.Output 在检查 Lshortfile/Llongfile 标志之

Go
大话西游666 2022-06-06 17:03:03
在 Go 的实现中(l *Logger) Output,为什么要先获取互斥锁 if l.flag&(Lshortfile|Llongfile) != 0 {?func (l *Logger) Output(calldepth int, s string) error {    now := time.Now() // get this early.    var file string    var line int    l.mu.Lock()    defer l.mu.Unlock()    if l.flag&(Lshortfile|Llongfile) != 0 {        // Release lock while getting caller info - it's expensive.        l.mu.Unlock()        var ok bool        _, file, line, ok = runtime.Caller(calldepth)        if !ok {            file = "???"            line = 0        }        l.mu.Lock()    }    l.buf = l.buf[:0]    l.formatHeader(&l.buf, now, file, line)    l.buf = append(l.buf, s...)    if len(s) == 0 || s[len(s)-1] != '\n' {        l.buf = append(l.buf, '\n')    }    _, err := l.out.Write(l.buf)    return err}那这个呢?func (l *Logger) Output(calldepth int, s string) error {    now := time.Now() // get this early.    var file string    var line int    if l.flag&(Lshortfile|Llongfile) != 0 {        var ok bool        _, file, line, ok = runtime.Caller(calldepth)        if !ok {            file = "???"            line = 0        }    }    // acquire mutex here, avoid aquire mutex twice.     l.mu.Lock()    defer l.mu.Unlock()    l.buf = l.buf[:0]    l.formatHeader(&l.buf, now, file, line)    l.buf = append(l.buf, s...)    if len(s) == 0 || s[len(s)-1] != '\n' {        l.buf = append(l.buf, '\n')    }    _, err := l.out.Write(l.buf)    return err}
查看完整描述

1 回答

?
饮歌长啸

TA贡献1951条经验 获得超3个赞

Logger.flag是受互斥体保护的字段,而不是常量。


log.Logger有一个SetFlags方法,可以随时从任何 goroutine 调用。该方法实现为:


// SetFlags sets the output flags for the logger.

// The flag bits are Ldate, Ltime, and so on.

func (l *Logger) SetFlags(flag int) {

    l.mu.Lock()

    defer l.mu.Unlock()

    l.flag = flag

}

文档本身清楚地表明记录器可以安全地并发使用:


一个 Logger 可以同时从多个 goroutine 中使用;...


为确保这一保证,任何Logger可以修改的字段都必须同步。如果您在l.flag没有正确同步的情况下访问,您将引入竞争条件。


查看完整回答
反对 回复 2022-06-06
  • 1 回答
  • 0 关注
  • 100 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信