Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 通过信号量执行线程同步后,无法同时运行三个线程_Python_Multithreading - Fatal编程技术网

Python 通过信号量执行线程同步后,无法同时运行三个线程

Python 通过信号量执行线程同步后,无法同时运行三个线程,python,multithreading,Python,Multithreading,我能够使用信号量值设置为1的信号量获得以下多线程代码的顺序输出。但是,现在不是3个进程同时运行,而是一次只运行一个线程。有没有一种方法可以让我同时运行三个线程,同时也可以获得顺序输出 from datetime import datetime import getpass import os import sys import time import re import json from random import random import threading from io import

我能够使用信号量值设置为1的信号量获得以下多线程代码的顺序输出。但是,现在不是3个进程同时运行,而是一次只运行一个线程。有没有一种方法可以让我同时运行三个线程,同时也可以获得顺序输出

from datetime import datetime
import getpass
import os
import sys
import time
import re
import json
from random import random
import threading
from io import StringIO
from time import gmtime, strftime
from pprint import pprint
from threading import *
screen_lock = Semaphore(value=1)

#------------------------------------------------------------------------------
def config_worker(port):
    if port == 'a':
       screen_lock.acquire()
       print('PASS : Tunnel1 is UP from  router 1')
       print('PASS : Tunnel2 is UP from  router 1')
       print('PASS : Tunnel3 is UP from  router 1')
       screen_lock.release()
       
    if port == 'b':
       screen_lock.acquire()
       print('PASS : Tunnel1 is UP from  router 2')
       print('PASS : Tunnel2 is UP from  router 2')
       print('PASS : Tunnel3 is UP from  router 2')
       screen_lock.release()
       
    if port == 'c':
       screen_lock.acquire()
       print('PASS : Tunnel1 is UP from  router 3')
       print('PASS : Tunnel2 is UP from  router 3')
       print('PASS : Tunnel3 is UP from  router 3')
       screen_lock.release()
    return

def connect():

    config_threads_list = []
    devices = ['a','b','c']
    for ports in devices:
        port = ports
        print ('Creating thread for: ', ports)
        config_threads_list.append(threading.Thread(target=config_worker, args=(port)))

    print ('\n---- Begin get config threading ----\n')
    for config_thread in config_threads_list:
        config_thread.start()

    for config_thread in config_threads_list:
        config_thread.join()



connect()
 
---- Begin get config threading ----

PASS : Tunnel1 is UP from  router 1
PASS : Tunnel2 is UP from  router 1
PASS : Tunnel3 is UP from  router 1
PASS : Tunnel1 is UP from  router 2
PASS : Tunnel2 is UP from  router 2
PASS : Tunnel3 is UP from  router 2
PASS : Tunnel1 is UP from  router 3
PASS : Tunnel2 is UP from  router 3
PASS : Tunnel3 is UP from  router 3
带信号量的输出。输出是正确的,但一次只运行一个线程。如何运行所有线程并打印顺序输出

from datetime import datetime
import getpass
import os
import sys
import time
import re
import json
from random import random
import threading
from io import StringIO
from time import gmtime, strftime
from pprint import pprint
from threading import *
screen_lock = Semaphore(value=1)

#------------------------------------------------------------------------------
def config_worker(port):
    if port == 'a':
       screen_lock.acquire()
       print('PASS : Tunnel1 is UP from  router 1')
       print('PASS : Tunnel2 is UP from  router 1')
       print('PASS : Tunnel3 is UP from  router 1')
       screen_lock.release()
       
    if port == 'b':
       screen_lock.acquire()
       print('PASS : Tunnel1 is UP from  router 2')
       print('PASS : Tunnel2 is UP from  router 2')
       print('PASS : Tunnel3 is UP from  router 2')
       screen_lock.release()
       
    if port == 'c':
       screen_lock.acquire()
       print('PASS : Tunnel1 is UP from  router 3')
       print('PASS : Tunnel2 is UP from  router 3')
       print('PASS : Tunnel3 is UP from  router 3')
       screen_lock.release()
    return

def connect():

    config_threads_list = []
    devices = ['a','b','c']
    for ports in devices:
        port = ports
        print ('Creating thread for: ', ports)
        config_threads_list.append(threading.Thread(target=config_worker, args=(port)))

    print ('\n---- Begin get config threading ----\n')
    for config_thread in config_threads_list:
        config_thread.start()

    for config_thread in config_threads_list:
        config_thread.join()



connect()
 
---- Begin get config threading ----

PASS : Tunnel1 is UP from  router 1
PASS : Tunnel2 is UP from  router 1
PASS : Tunnel3 is UP from  router 1
PASS : Tunnel1 is UP from  router 2
PASS : Tunnel2 is UP from  router 2
PASS : Tunnel3 is UP from  router 2
PASS : Tunnel1 is UP from  router 3
PASS : Tunnel2 is UP from  router 3
PASS : Tunnel3 is UP from  router 3
最可能的问题是锁。试一试


正在运行所有线程-您可以看出这一点,因为所有输出都已生成

由于信号量的原因,语句总是以三个块的形式出现

如果您想要更随机的序列,请尝试添加睡眠(我还添加了一个打印以显示哪个端口线程正在启动):

现在,当您运行此代码时,可以获得不同的序列,请尝试几次:

首次运行:

Creating thread for:  a
Creating thread for:  b
Creating thread for:  c

---- Begin get config threading ----

Starting thread a
Starting thread b
Starting thread c
PASS : Tunnel1 is UP from  router 3
PASS : Tunnel2 is UP from  router 3
PASS : Tunnel3 is UP from  router 3
PASS : Tunnel1 is UP from  router 1
PASS : Tunnel2 is UP from  router 1
PASS : Tunnel3 is UP from  router 1
PASS : Tunnel1 is UP from  router 2
PASS : Tunnel2 is UP from  router 2
PASS : Tunnel3 is UP from  router 2
第二轮:

Creating thread for:  a
Creating thread for:  b
Creating thread for:  c

---- Begin get config threading ----

Starting thread a
Starting thread b
Starting thread c
PASS : Tunnel1 is UP from  router 2
PASS : Tunnel2 is UP from  router 2
PASS : Tunnel3 is UP from  router 2
PASS : Tunnel1 is UP from  router 1
PASS : Tunnel2 is UP from  router 1
PASS : Tunnel3 is UP from  router 1
PASS : Tunnel1 is UP from  router 3
PASS : Tunnel2 is UP from  router 3
PASS : Tunnel3 is UP from  router 3
或者,如果您注释掉
屏幕锁定.acquire()
/
屏幕锁定.release()
行,则会得到一个更复杂的序列(在本例中,我将睡眠(0.0001)保留在中,但没有睡眠,序列也会发生变化,可能是因为线程打开打印的I/O):


伙计们,任何建议都会有帮助的。如果可以的话,请告诉我sameThreads实际上并不是同时运行的,基本上线程只有在基于i/o原因的情况下才会切换,但我相信可以使用例如time.sleep(0)让一个线程产生,以便Python运行另一个线程(如果有一个线程可以运行的话)。如果取消锁定并在每个打印语句后添加
time.sleep(0)
,您可能会看到这种情况。但是,控制线程切换的目标是矛盾的——如果您认为需要完全控制线程执行的顺序,那么您可能不应该使用线程,编写sequential.Correction——不要使用0,例如使用
time.sleep(0.0001')
请看hi barny,还有什么好主意吗?不要相信有什么“问题”,这只是Python线程的工作方式。hi saket很抱歉,多处理导致我的windows pc挂起,您有更好的解决方案吗,在Windows上添加代码后,我无法收到任何输出,该代码几乎不可避免地会将您锁定-您需要使用
保护要作为“主”线程执行的代码,如果
name\uuuuuuuuu==''main\uuuuuuu':
请参阅所有示例都使用此功能的文档。多处理与线程是截然不同的。
Creating thread for:  a
Creating thread for:  b
Creating thread for:  c

---- Begin get config threading ----

Starting thread a
Starting thread b
Starting thread c
PASS : Tunnel1 is UP from  router 3
PASS : Tunnel1 is UP from  router 1
PASS : Tunnel2 is UP from  router 3
PASS : Tunnel2 is UP from  router 1
PASS : Tunnel3 is UP from  router 3
PASS : Tunnel3 is UP from  router 1
PASS : Tunnel1 is UP from  router 2
PASS : Tunnel2 is UP from  router 2
PASS : Tunnel3 is UP from  router 2