【问题标题】:Why are results different between using threads and processes?为什么使用线程和进程的结果不同?
【发布时间】:2021-10-06 23:11:23
【问题描述】:

在实践python的线程和进程的时候,发现线程和进程在处理一些函数的时候打印结果会不一样。我不是很明白原因,所以我把代码和打印结果一起发了。以及如何使进程部分和线程部分的结果一致?

使用线程时,一切正常:

import os, time, random, threading, multiprocessing

list = ['python', 'django', 'tornado', 'flask', 'bs5', 'requests', 'uvloop']

new_lists = []

def work():
    if len(list) == 0:
        return
    data = random.choice(list)
    list.remove(data)
    new_data = '%s_new' % data
    new_lists.append(new_data)
    time.sleep(1)

if __name__ == '__main__':
    start = time.time()
    print('old list lenc is %s' % len(list))

    for i in range(len(list)):
        t = threading.Thread(target=work)
        t.start()
    t.join()

    print('old list:', list)
    print('new list', new_lists, len(new_lists))
    print('time is %s' % (time.time() - start))

哪个会打印:(结果很好)

old list lenc is 7
old list: []
new list ['uvloop_new', 'python_new', 'bs5_new', 'tornado_new', 'django_new', 'requests_new', 'flask_new'] 7
time is 1.0153822898864746

但是,当线程切换到进程时,错误发生了:

import os, time, random, threading, multiprocessing

list = ['python', 'django', 'tornado', 'flask', 'bs5', 'requests', 'uvloop']

new_lists = []


def work():
    if len(list) == 0:
        return
    data = random.choice(list)
    list.remove(data)
    new_data = '%s_new' % data
    new_lists.append(new_data)
    time.sleep(1)


if __name__ == '__main__':
    start = time.time()
    print('old list lenc is %s' % len(list))

    for i in range(len(list)):
        t = multiprocessing.Process(target=work)
        t.start()
    t.join()

    print('old list:', list)
    print('new list', new_lists, len(new_lists))
    print('time is %s' % (time.time() - start))

将打印的内容:(结果与预期不符)

old list lenc is 7
old list: ['python', 'django', 'tornado', 'flask', 'bs5', 'requests', 'uvloop']
new list [] 0
time is 1.4266910552978516

【问题讨论】:

  • 每个进程都有自己的变量。所以你有 8 个版本的 new_lists 并且主进程中的一个永远不会改变。

标签: python multithreading concurrency parallel-processing process


【解决方案1】:

在多线程中,您有共享内存,但在多处理中,您没有共享内存。因此,当您尝试在每个进程中更改全局变量时,您会丢失数据。 这个问题没有办法解决,你应该根据你的项目情况选择正确的选项。如果您需要在每个并行函数中操作共享数据,您应该使用线程。 尽管您可以使用 Queue 在多处理中的每个进程之间传递数据。 https://docs.python.org/3/library/queue.html

【讨论】:

    猜你喜欢
    • 2020-10-12
    • 1970-01-01
    • 2014-03-20
    • 1970-01-01
    • 1970-01-01
    • 2016-10-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多