线程队列,代码是对的吗?

时间:2017-11-07 20:51:43

标签: python multithreading queue

我写了一个小型多主机在线扫描仪。所以我的问题是代码是否正确?我的意思是,程序会做它应该做的事情,但是如果我在top命令中查看终端,它会不时向我显示很多僵尸线程。

扫描和穿线功能代码:

def scan(queue):
    conf.verb = 0

    while True:
        try:
            host = queue.get()
            if host is None:
                sys.exit(1)
            icmp = sr1(IP(dst=host)/ICMP(),timeout=3)
            if icmp:
                with Print_lock:
                    print("Host: {} online".format(host))
                saveTofile(RngFile, host)

        except Empty:
            print("Done")
        queue.task_done()

def threader(queue, hostlist):
    threads = []
    max_threads = 223

    for i in range(max_threads):
        thread = Thread(target=scan, args=(queue,))
        thread.start()
        threads.append(thread)

    for ip in hostlist:
        queue.put(ip)
    queue.join()

    for i in range(max_threads):
        queue.put(None)

    for thread in threads:
        thread.join()

P.S。抱歉我的英语很糟糕

1 个答案:

答案 0 :(得分:1)

如果你有比线程更多的线程,那么你并没有从产生它们中获得任何好处,更糟糕的是python具有全局解释器锁定,因此除非你使用多个进程,否则你不会得到真正的多线程。使用多处理并将max_threads设置为multiprocessing.cpu_count()。

更好的是,你可以使用游泳池。

from multiprocessing import Pool, cpu_count

with Pool(cpu_count()) as p:
    results = p.map(scan, hostlist) 
# change scan to take host directly instead of from a queue
# if you change 

就是这样,不要乱用队列并填充无以确保你杀死所有进程。

我应该添加,确保在主模块中创建进程池!您的代码完整应该如下所示:

from multiprocessing import Pool, cpu_count

def scan(host):
    # whatever

if __name__ == "__main__":
    with Pool(cpu_count()) as p:
        results = p.map(scan, hostlist)