程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式師世界 >> 編程語言 >  >> 更多編程語言 >> Python

Multithreading settings in python (synchronous)

編輯:Python

List of articles

  • ** Synchronization between threads **
  • Thread lock
  • Some of the advantages and disadvantages of multithreading

This article will explain Python In programming language Multithreading The concept of thread synchronization in the case of processing .

Synchronization between threads

Thread synchronization is defined as a mechanism , It ensures that two or more concurrent threads do not execute something called Key segment Specific segments of .

The key part is the part of the program that accesses the shared resources .

for example , In the following illustration ,3 Threads trying to access shared resources or critical parts at the same time .

Concurrent access to shared resources can lead to Contention .

When two or more threads can access the shared data and try to change the shared data at the same time , Contention will occur . therefore , The value of a variable may be unpredictable , And it changes according to the context switching time of the process .

Consider the following procedure to understand the concept of contention conditions :

import threading
# Global variables x
x = 0
def increment():
""" Used to increment global variables x Function of """
global x
x += 1
def thread_task():
""" The task of the thread calls the incremental function 100000 Time ."""
for _ in range(10000000):
increment()
def main_task():
global x
# Put the global variable x Set to 0
x = 0
# Create thread
t1 = threading.Thread(target=thread_task)
t2 = threading.Thread(target=thread_task)
# Open thread
t1.start()
t2.start()
# Wait for the thread to complete
t1.join()
t2.join()
if __name__ == "__main__":
for i in range(10):
main_task()
print(" iteration {0}: x = {1}".format(i, x))

Running results :

In the above procedure :

  • In function main_task Create two threads in t1 and t2, And global variables x Set to 0.
  • Each thread has an objective function thread_task among The incremental Function called 100000 Time .
  • increment The function will the global variable in every call x Increasing 1.

x The expected final value of is 200000, But we are in the function 10 Sub iteration Get in main_task Are some different values .

( If you get the same result every time you run , It may be because your computer has good performance , Try this to enlarge thread_task() Method data , If one or more zeros are added , Such as 10000000 Time )

This happens because the thread shares variables x Concurrent access to .x This unpredictability of values is nothing more than Race condition .

Here is a chart , Shows how this happens in the above program Contention condition

Please note that , Above picture x Expected value for 12, But because of the contention condition , The result is 11!

therefore , We need a tool to properly synchronize multiple threads .

Here we will use thread lock

Thread lock

Threads The module provides one Lock Class to handle contention conditions . Locking is provided by the operating system Semaphore Object implemented .

A semaphore is a synchronization object , Used to control multiple processes / Thread access to common resources in parallel programming environment . It's just the operating system ( Or kernel ) The value of the specified location in the storage , Each process / Threads can check the value , Then make changes . Based on the value found , process / Threads can use this resource , Or you may find it already in use , And you have to wait a while to try again . Semaphores can be binary (0 or 1), You can also have other values . Usually , Processes that use semaphores / The thread will check the value , then , If it uses resources , Then change the value to reflect this value , So that subsequent semaphore users will know to wait .

Lock Class provides the following methods :

  • obtain ([ Blocking ]) : Get the lock . Locks can be blocked , It can also be non blocking .

    • When the blocking parameter is set to True( The default value is ) When called , Thread execution will be blocked , Until the lock is unlocked , Then the lock is set to lock and returns True.
    • When the blocking parameter is set to False Under the circumstances Invocation time , Does not block thread execution . If the lock is unlocked , Set it to lock and return to True, Otherwise, it will return immediately False.
  • Release () : Release the lock .

    • After locking , Reset it to unlocked , Then return . If any other thread is blocked, wait for the lock to unlock , Please allow only one of the threads to continue .
    • If the lock is unlocked , Will trigger Thread error .

Consider the example given below :

import threading
# Global variables x
x = 0
def increment():
""" Used to increment global variables x Function of """
global x
x += 1
def thread_task(lock):
""" The task of the thread calls the incremental function 100000 Time ."""
for _ in range(100000):
lock.acquire()
increment()
lock.release()
def main_task():
global x
# Set the global variable to 0
x = 0
# Create thread lock
lock = threading.Lock()
# Create thread
t1 = threading.Thread(target=thread_task, args=(lock,))
t2 = threading.Thread(target=thread_task, args=(lock,))
# Open thread
t1.start()
t2.start()
# Wait for all threads to finish
t1.join()
t2.join()
if __name__ == "__main__":
for i in range(10):
main_task()
print(" iteration {0}: x = {1}".format(i, x))

Running results :

Let's try to understand the above code step by step :

  • First , Use the following command to create Lock object :

     lock = threading.Lock()
    
  • then , take lock Pass as an objective function parameter :

     t1 = threading.Thread(target=thread_task, args=(lock,))
    t2 = threading.Thread(target=thread_task, args=(lock,))
    
  • In the key part of the objective function , We use lock.acquire() Method application lock. Once you get the lock , In the use of lock.release() Method before releasing the lock , No other thread has access to critical parts ( Here is The incremental function ).

     lock.acquire()
    increment()
    lock.release()
    

    As you can see in the results ,x The final value of is displayed as 200000( This is the expected end result ).

Here is a chart , The implementation of lock in the above program is described :

Some of the advantages and disadvantages of multithreading

Last , Here are some of the advantages and disadvantages of multithreading :

advantage :

  • It doesn't stop users . This is because threads are independent of each other .
  • Because threads execute tasks in parallel , Therefore, we can make better use of system resources .
  • Enhanced performance on multiprocessor computers .
  • Multithreaded servers and interactive GUI Only use multithreading .

Disadvantages :

  • As the number of threads increases , Complexity will also increase .
  • Shared resources ( object 、 data ) Synchronization of is necessary .
  • Debugging is very difficult , Sometimes the results are unpredictable .
  • Potential deadlocks leading to starvation , That is, some threads may not provide a bad design
  • Constructing and synchronizing threads takes a lot of CPU/ Memory .

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式師世界 All Rights Reserved