큰 numpy
배열을 상태로 저장하는 클래스가 있습니다. 이로 인해 multiprocessing.Pool
이 매우 느려집니다. 이 코드는 (그리고 않음)에 약 2 초 실행해야 즉, 내가 CPU에 4 개의 코어를 가지고상태가 큰 배열로 다중 처리
from multiprocessing import Pool
import numpy
import time
from tqdm import tqdm
class MP(object):
def __init__(self, mat):
self.mat = mat
def foo(self, x):
time.sleep(1)
return x*x + self.mat.shape[0]
def bar(self, arr):
results = []
with Pool() as p:
for x in tqdm(p.imap(self.foo, arr)):
results.append(x)
return results
if __name__ == '__main__':
x = numpy.arange(8)
mat = numpy.random.random((1,1))
h = MP(mat)
res = h.bar(x)
print(res)
: 여기 MRE입니다. (tqdm
은 진행 막대로 2 초를 보여 주지만이 예제에서는 실제로 필요하지 않습니다.) 그러나 주 프로그램에서 내가 mat = numpy.random.random((10000,10000))
을 실행하면 실행하는 데 오래 걸립니다. 나는 Pool
이 각 작업자에 대해 mat
사본을 만들고 있기 때문에 이것이 의심 스럽지만 mat
이 imap
호출에 직접적으로 관여하지 않았기 때문에 이것이 어떻게 작동하는지 잘 모르겠습니다. 따라서 내 질문은 다음과 같습니다.
- 왜 이런 현상이 발생합니까? (즉, 클래스 내에서
Pool
은 어떻게 작동합니까? 정확히 무엇을 피클 하는가, 참조로 전달되는 내용은 무엇입니까?) - 이 문제를 해결할 수있는 방법은 무엇입니까?
편집 : 내 진짜 문제를보다 잘 나타내는 인, mat
을 사용하려면 foo
을 수정.
메인 프로그램에서'x' 크기는 얼마나됩니까? –
메인 프로그램에서'p.imap'에 넘겨주는 함수가'MP'의 메소드 일 필요가 있습니까, 아니면 언 바운드 함수가 될 수 있습니까? –
@JeremyMcGibbon 좋은 지적. 나는 나의 모범이 나의 실제 문제를 잘 표현하지 못했다고 생각한다. 따라서 함수는'mat'에서 실제로 읽히기 때문에'MP'의 메소드가 될 필요가 있습니다. – ved