Pythonでグローバル変数を共有するマルチスレッドの問題

あなたが前に読まなければならないいくつかのPの単語を書いてください:

グローバル変数のデータは、Pythonの複数のスレッド間で共有できます。

ただし、グローバル変数を複数のスレッドと共有すると問題が発生する可能性があります。

2つのスレッドt1とt2の両方がグローバル変数g_num(デフォルトは0)に1を加算すると仮定すると、t1とt2はそれぞれg_numに10回加算され、g_numの最終結果は20になります。

ただし、複数のスレッドが同時に動作するため、次の状況が発生する可能性があります。

g_num = 0の場合、t1はg_num=0を取得します。このとき、システムはt1を「スリープ」状態にスケジュールし、t2を「実行中」状態に変換し、t2もg_num=0を取得します。

次に、t2は取得した値に1を加算し、それをg_numに割り当てるため、g_num=1になります。

次に、システムはt2を「スリープ」に、t1を「実行中」にスケジュールします。スレッドt1は、以前に取得した0に1を追加した後、g_numに0を再度追加します。

これにより、t1とt2の両方がg_numに1を加算しますが、結果はg_num=1のままになります。

例を見てみましょう:

import threading
import time

g_num = 0

def work1(num):
    global g_num
    for i in range(num):
        g_num += 1
    print("----in work1, g_num is %d---" % g_num)

def work2(num):
    global g_num
    for i in range(num):
        g_num += 1
    print("----in work2, g_num is %d---" % g_num)

print("---线程创建之前g_num is %d---" % g_num)

t1 = threading.Thread(target=work1, args=(100,))
t1.start()

t2 = threading.Thread(target=work2, args=(100,))
t2.start()

# 确保子线程都运行结束
while len(threading.enumerate()) != 1:
    time.sleep(1)

print("2个线程对同一个全局变量操作之后的最终结果是:%s" % g_num)

演算結果:

---线程创建之前g_num is 0---
----in work1, g_num is 100---
----in work2, g_num is 200---
2个线程对同一个全局变量操作之后的最终结果是:200

一見問題ないようです。これは、データが小さすぎるため、データを大きくするようになりました。

'''
遇到问题没人解答?小编创建了一个Python学习交流QQ群:660193417
寻找有志同道合的小伙伴,互帮互助,群里还有不错的视频学习教程和PDF电子书!
'''
import threading
import time

g_num = 0

def work1(num):
    global g_num
    for i in range(num):
        g_num += 1
    print("----in work1, g_num is %d---" % g_num)

def work2(num):
    global g_num
    for i in range(num):
        g_num += 1
    print("----in work2, g_num is %d---" % g_num)

print("---线程创建之前g_num is %d---" % g_num)

t1 = threading.Thread(target=work1, args=(1000000,))
t1.start()

t2 = threading.Thread(target=work2, args=(1000000,))
t2.start()

# 确保子线程都运行结束
while len(threading.enumerate()) != 1:
    time.sleep(1)

print("2个线程对同一个全局变量操作之后的最终结果是:%s" % g_num)

演算結果:

---线程创建之前g_num is 0---
----in work2, g_num is 1048576---
----in work1, g_num is 1155200---
2个线程对同一个全局变量操作之后的最终结果是:1155200

数値が大きいほど、問題が発生する可能性が高くなり、データの偏りが大きくなります。

結論は

複数のスレッドが同じグローバル変数で同時に動作する場合、リソース競合の問題が発生し、データの結果が不正確になります。

おすすめ

転載: blog.csdn.net/m0_67575344/article/details/124150861