デッドロックを回避する方法:
デッドロックは、2 つのスレッドが互いのリソースの解放を待機するときに発生します。 Python インタプリタはデッドロック状況を監視せず、積極的に対処策を講じないため、マルチスレッド プログラミングを実行する場合はデッドロックを回避するための措置を講じる必要があります。
デッドロックが発生すると、プログラム全体で例外も生成されず、プロンプトも表示されませんが、すべてのスレッドがブロックされ、続行できなくなります。
デッドロックは非常に発生しやすく、特にシステム内に複数の同期モニターがある場合、次のプログラムはデッドロックを引き起こします:
import threading import time class A: def __init__(self): self.lock = threading.RLock() def foo(self, b): try: self.lock.acquire() print("当前线程名: " + threading.current_thread().name\ + " 进入了A实例的foo()方法" ) # ① time.sleep(0.2) print("当前线程名: " + threading.current_thread().name\ + " 企图调用B实例的last()方法") # ③ b.last() finally: self.lock.release() def last(self): try: self.lock.acquire() print("进入了A类的last()方法内部") finally: self.lock.release() class B: def __init__(self): self.lock = threading.RLock() def bar(self, a): try: self.lock.acquire() print("当前线程名: " + threading.current_thread().name\ + " 进入了B实例的bar()方法" ) # ② time.sleep(0.2) print("当前线程名: " + threading.current_thread().name\ + " 企图调用A实例的last()方法") # ④ a.last() finally: self.lock.release() def last(self): try: self.lock.acquire() print("进入了B类的last()方法内部") finally: self.lock.release() a = A() b = B() def init(): threading.current_thread().name = "主线程" # 调用a对象的foo()方法 a.foo(b) print("进入了主线程之后") def action(): threading.current_thread().name = "副线程" # 调用b对象的bar()方法 b.bar(a) print("进入了副线程之后") # 以action为target启动新线程 threading.Thread(target=action).start() # 调用init()函数 init()
上記のプログラムを実行すると、表示される効果を確認してください。図 1 にあります。
図 1 デッドロック効果
図 1 からわかるように、プログラムは下向きに実行することも、異常をスローすることもできません。 「行き詰まり」。その理由は、上記のプログラムのオブジェクト A とオブジェクト B のメソッドが両方ともスレッドセーフなメソッドであるためです。
プログラム内では 2 つのスレッドが実行されています。セカンダリ スレッドのスレッド実行本体は action() 関数で、メイン スレッドのスレッド実行本体は init() 関数です (メイン プログラムの呼び出しinit() 関数)。 action() 関数では、B オブジェクトが bar() メソッドを呼び出し、init() 関数では、A オブジェクトが foo() メソッドを呼び出します。
図 1 は、action() 関数が最初に実行され、B オブジェクトの bar() メソッドを呼び出すことを示しています。bar() メソッドに入る前に、スレッドは B オブジェクトの Lock をロックします (プログラムが 2 番のコードまで実行され、セカンダリ スレッドが 0.2 秒間一時停止します); CPU は別のスレッドの実行に切り替え、A オブジェクトに foo() メソッドを実行させるため、メイン スレッドが foo( foo() メソッドに入る前に、このスレッドはオブジェクト A の Lock をロックします (プログラムがコード①を実行すると、メインスレッドも 0.2 秒停止します)。
次に、セカンダリ スレッドが最初に起動し、コード ④ に到達するまで下方向に実行を続け、A オブジェクトの last() メソッドを呼び出すことを期待します (このメソッドを実行する前に、A オブジェクトの Lock最初にロックする必要があります) が、この時点ではメイン スレッドが A オブジェクトのロックを維持しているため、セカンダリ スレッドはブロックされます。
メインスレッドは次に起動し、B オブジェクトの last() メソッドを呼び出すコード ③ に到達するまで下方向に実行を続ける必要があります (このメソッドを実行する前に、B オブジェクトは最初に Lock されている必要があります) ) ですが、この時点ではセカンダリ スレッドは B オブジェクトのロックを解放しません。
この時点で、メイン スレッドはオブジェクト A のロックを保持してオブジェクト B がロックされるのを待機し、セカンダリ スレッドはオブジェクト B のロックを保持してオブジェクト A がロックされるのを待機しているように見えます。 2 つのスレッドは互いに待機し、ロックが先に解放されるため、デッドロックが発生します。
プログラムでデッドロックが発生してはなりません。プログラムを作成するときは、デッドロックを回避するように努める必要があります。 デッドロックの問題を解決するには、以下の一般的な方法があります:
複数のロックを避けてください。同じスレッド上で複数のロックをロックしないようにしてください。例えば、上記のデッドロックプログラムでは、メインスレッドは2つのオブジェクトAとBのLockをロックする必要があり、セカンダリスレッドも2つのオブジェクトAとBのLockをロックする必要があり、デッドロックの危険が潜んでいます。
のロック シーケンスは同じです。複数のスレッドが複数のロックをロックする必要がある場合は、同じ順序でロックを要求するようにする必要があります。たとえば、上記のデッドロック プログラムでは、メイン スレッドは最初にオブジェクト A のロックをロックし、次にオブジェクト B のロックをロックしますが、セカンダリ スレッドは最初にオブジェクト B のロックをロックし、次にオブジェクト A のロックをロックします。このロック シーケンスにより、ネストされたロックが簡単に形成され、デッドロックが発生する可能性があります。この問題は、メインスレッドとセカンダリスレッドが同じ順序でロックすれば回避できます。
- #タイミング ロックを使用します。プログラムは、ロックするためにacquire()メソッドを呼び出すときにタイムアウト・パラメータを指定できます。このパラメータは、デッドロックのロックを解除できるように、タイムアウト秒後にロックが自動的に解放されることを指定します。
- デッドロックの検出。デッドロック検出は、アルゴリズム メカニズムに依存するデッドロック防止メカニズムであり、主に順次ロックが不可能で時間指定ロックが使用できないシナリオを対象としています。
以上がデッドロックを回避するにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ホットAIツール

Undresser.AI Undress
リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover
写真から衣服を削除するオンライン AI ツール。

Undress AI Tool
脱衣画像を無料で

Clothoff.io
AI衣類リムーバー

Video Face Swap
完全無料の AI 顔交換ツールを使用して、あらゆるビデオの顔を簡単に交換できます。

人気の記事

ホットツール

SecLists
SecLists は、セキュリティ テスターの究極の相棒です。これは、セキュリティ評価中に頻繁に使用されるさまざまな種類のリストを 1 か所にまとめたものです。 SecLists は、セキュリティ テスターが必要とする可能性のあるすべてのリストを便利に提供することで、セキュリティ テストをより効率的かつ生産的にするのに役立ちます。リストの種類には、ユーザー名、パスワード、URL、ファジング ペイロード、機密データ パターン、Web シェルなどが含まれます。テスターはこのリポジトリを新しいテスト マシンにプルするだけで、必要なあらゆる種類のリストにアクセスできるようになります。

ゼンドスタジオ 13.0.1
強力な PHP 統合開発環境

VSCode Windows 64 ビットのダウンロード
Microsoft によって発売された無料で強力な IDE エディター

MantisBT
Mantis は、製品の欠陥追跡を支援するために設計された、導入が簡単な Web ベースの欠陥追跡ツールです。 PHP、MySQL、Web サーバーが必要です。デモおよびホスティング サービスをチェックしてください。

メモ帳++7.3.1
使いやすく無料のコードエディター

ホットトピック









