多线程存在共享全局变量的问题:
多线程都是在同一个进程中运行的,因此在进程中的全局变量所有线程都是可共享的。
这就造成一个问题,因为线程执行的顺序时无序的,有可能会造成数据错误
以上结果正常的话,应该是10000000和20000000,但因为多线程运行的不确定性,因此最后的结果可能是随机的
扩展:
启动一个线程时,线程并不会立即执行,而是等待CPU的资源调度,因次每个线程执行顺序是随机无序的,具有不确定性
# 多线程共享全局变量的问题 import threading value = 0 value_2 = 0 def add_value(): # 如果在函数中修改全局变量,需要global声明全局变量 global value,value_2 for x in range(100): value += 1 print("{0}\tvalue的值:{1}".format(threading.current_thread().name,value)) for y in range(10000000): value_2 += 1 print("{0}\tvalue_2的值:{1}".format(threading.current_thread().name,value_2)) def main(): for x in range(2): thread = threading.Thread(target=add_value) thread.start() if __name__ == "__main__": main()
执行结果
锁机制和threading.Lock类:
为了解决共享全局变量的问题,threading提供了一个Lock类。
这个类可以在某个线程访问某个变量的时候加锁,其它线程此时就不能进来,直到当线程处理完后,把锁释放了,其它线程才能进来处理。
使用锁的原则:
1.把尽量少的和不耗时的代码放到锁中执行
2.代码执行完成后,要记得释放锁
# 锁机制和threading.Lock类 import threading value = 0 value_2 = 0 # 生成一个锁对象 gLock = threading.Lock() def add_value(): # 如果在函数中修改全局变量,需要global声明全局变量 global value,value_2 # 加锁 gLock.acquire() for x in range(100): value += 1 print("{0}\tvalue的值:{1}".format(threading.current_thread().name,value)) for y in range(10000000): value_2 += 1 print("{0}\tvalue_2的值:{1}".format(threading.current_thread().name,value)) # 释放锁 gLock.release() def main(): for x in range(2): thread = threading.Thread(target=add_value) thread.start() if __name__ == "__main__": main()