Middle+
Программаны ишга туширганда нима чиқади: func main() { counter := make([]int, 0, 1000) var wg sync.WaitGroup for i := 0; i < 1000; i++ { wg.Add(1) go func() { defer wg.Done() counter = append(counter, i) time.Sleep(10 * time.Millisecond) // Ишни имитация қилиш }() } wg.Wait() fmt.Println(len(counter)) }
sobes.tech AI
Ҷавоб аз AI
Програмата съдържа състезание с данни при запис в сегмента counter от няколко горутини без синхронизация. Това води до непредсказуемо поведение.
Какво се случва:
- Създава се сегмент
counterс дължина 0 и капацитет 1000. - Стартират се 1000 горутини, всяка от които се опитва да добави стойността
iкъм сегмента. - Операцията
appendне е потокобезопасна, няколко горутини модифицират сегмента едновременно. - Поради състезание с данни може да има загуба на данни, повреждане на сегмента или паника.
На изхода:
- Стойността
len(counter)може да бъде по-малка от 1000, тъй като някои записи могат да бъдат загубени. - Може да се случи паника или неправилен изход.
Правилният подход е да се използва мютекс или канал за синхронизиране на достъпа до сегмента:
var mu sync.Mutex
for i := 0; i < 1000; i++ {
wg.Add(1)
go func(val int) {
defer wg.Done()
mu.Lock()
counter = append(counter, val)
mu.Unlock()
time.Sleep(10 * time.Millisecond)
}(i)
}
Или да се използват потокобезопасни структури от данни.