func (l *Logger) SetOutput(w io.Writer) {
	l.mu.Lock()
	defer l.mu.Unlock()
	l.out = w
	isDiscard := int32(0)
	if w == io.Discard {
		isDiscard = 1
	}
	atomic.StoreInt32(&l.isDiscard, isDiscard)
}
上面这段代码用了 atomic.StoreInt32 的意义在哪里?
func (l *Logger) SetOutput(w io.Writer) {
	l.mu.Lock()
	defer l.mu.Unlock()
	l.out = w
	if w == io.Discard {
		l.isDiscard = 1
	}
}
跟这样写有啥区别?
|      1GopherDaily      2023-02-08 16:39:33 +08:00  3 In the terminology of the Go memory model, if the effect of an atomic operation A is observed by atomic operation B, then A “synchronizes before” B. Additionally, all the atomic operations executed in a program behave as though executed in some sequentially consistent order. This definition provides the same semantics as C++'s sequentially consistent atomics and Java's volatile variables. 搜一下 Memory Model | 
|  |      2bolide2005      2023-02-08 16:42:47 +08:00  1 emmm ,我觉得是,想象一个极端场景,16 位机器存储一个 32 位的数字,那么就会需要至少两条 CPU 指令,分别写高位和低位,这样就存在脏读的可能性 | 
|  |      3bolide2005      2023-02-08 16:43:27 +08:00 所以需要一个原子操作来防止这种情况 | 
|  |      4bolide2005      2023-02-08 16:52:31 +08:00 @GopherDaily #1 学习了 | 
|      5lolizeppelin      2023-02-08 18:09:45 +08:00 因为有好几个地方无锁读取 isDiscard 所以都使用 atomic 来无锁化读写 isDiscard | 
|      6010203kk      2023-02-08 20:06:44 +08:00 都是高手啊。 | 
|  |      7gamexg      2023-02-08 21:27:46 +08:00 我写过类似的代码,锁内部还是用原子操作。 原因是,其他地方不想加锁,而只是使用原子操作。 | 
|      8littlewing      2023-02-08 21:37:15 +08:00 按理说所有读取和写入都加锁的话,没必要用 atomic | 
|      9GopherDaily      2023-02-08 21:39:39 +08:00 @bolide2005 Java 的 Memory Model 网上资料多一点,原理和要做的事都一样的 | 
|  |      10wangritian      2023-02-08 23:43:14 +08:00 除了#2 所说 16 位机器问题,atomic 还确保了 l.isDiscard=0/1 一定在 l.out = w 之后,不会乱序执行,进而确保无锁使用 l.isDiscard 时它的结果一定符合 w == io.Discard ,推荐按#1 所说 Memory Model 完整了解一下 | 
|  |      11lasuar      2023-02-09 00:33:52 +08:00 答案应该是 5 楼吧。 | 
|      12yulon      2023-02-09 02:37:24 +08:00 无锁读取,有锁修改,比读写锁竞争少 | 
|  |      13Rehtt      2023-02-09 08:40:55 +08:00 应该在其他地方 l.isDiscard 被并发无锁读写,所以用了原子操作 | 
|  |      14malaohu      2023-02-09 09:36:44 +08:00 | 
|  |      15macscsbf      2023-02-14 16:00:26 +08:00 @wangritian 我不太懂,加了锁的话不是就保证了内存的顺序,保证 l.isDiscard=0/1 一定在 l.out = w 之后, atomic 应该只是因为其他地方存在无锁读取吧 |