프로그래밍/Python

[Python] 프로세스간 데이터 공유 : Array

채윤아빠 2022. 6. 16. 14:25
728x90
반응형

개요

다중 프로세스간 데이터를 공유할 수 있는 다양한 클래스들이 "multiprocessing"에서 제공됩니다.

 

Array, Pipe, Queue, Value

 

그 중에서 Array를 이용한 데이터 공유 방법에 대하여 정리해 둡니다.


Array 객체 생성

Array 클래스로 객체를 생성하는 방법은 다음과 같습니다. list 객체와는 약간 다릅니다.

from multiprocessing import Array

arr = Array('i', range(10))
print(arr)
print(arr[:])
arr2 = Array('i', [0, 0, 0, 1, 2, 3, 4])
print(arr2)
print(arr2[:])

위 코드의 실행 결과는 다음과 같습니다.

<SynchronizedArray wrapper for <multiprocessing.sharedctypes.c_long_Array_7 object at 0x000001EE7B9D6AC0>>
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
<SynchronizedArray wrapper for <multiprocessing.sharedctypes.c_long_Array_7 object at 0x000001EE7BA046C0>>
[0, 0, 0, 1, 2, 3, 4]

하나씩 데이터를 입력할 때는 항목별 색인을 지정하여 할당하거나, 값을 읽을 수 있습니다.

print(arr[0])
arr[0] = 10
print(arr[:])

위 코드에 대한 실행 결과는 다음과 같습니다.

0
[10, 1, 2, 3, 4, 5, 6, 7, 8, 9]

배열의 범위를 지정하여 값들을 읽어오거나, 한꺼번에 할당도 가능합니다.

print(arr[2:7])
arr[2:7] = [7, 6, 5, 4, 3]
print(arr[:])

위 코드를 실행한 결과는 다음과 같습니다.

[2, 3, 4, 5, 6]
[10, 1, 7, 6, 5, 4, 3, 7, 8, 9]

Lock을 활용한 여러 공유 객체간 동기화

개발을 진행하다 보면, 특정 배열에 대하여 프로세스간 공유가 필요한 경우도 있겠지만 배열 1개 뿐만 아니라, 다른 데이터들도 함께 동기화가 필요한 경우가 있을 수 있습니다.
이런 경우에 유용한 것이 Array, Value 클래스 생성자의 "lock" 파라미터 입니다.

다음은 "lock" 파라미터를 활용한 예제입니다.

from multiprocessing import Process, Lock
from multiprocessing.sharedctypes import Value, Array
from ctypes import Structure, c_double

class Point(Structure):
    _fields_ = [('x', c_double), ('y', c_double)]

def modify(n, x, s, A):
    n.value **= 2
    x.value **= 2
    s.value = s.value.upper()
    for a in A:
        a.x **= 2
        a.y **= 2

if __name__ == '__main__':
    lock = Lock()

    n = Value('i', 7)
    x = Value(c_double, 1.0/3.0, lock=False)
    s = Array('c', b'hello world', lock=lock)
    A = Array(Point, [(1.875,-6.25), (-5.75,2.0), (2.375,9.5)], lock=lock)

    p = Process(target=modify, args=(n, x, s, A))
    p.start()
    p.join()

    print(n.value)
    print(x.value)
    print(s.value)
    print([(a.x, a.y) for a in A])

위 코드에서는 n은 별개의 내부 "Lock"를 이용하고 있고, x는 "Lock"을 이용하지 않습니다.
s와 A는 동일한 "lock"를 이용하는데, 특정 프로세스에서 A를 접근하고 있다면 A뿐만 아니라 s도 타 프로세스에서 접근할 수 없게 됩니다.

위 코드를 실행한 결과는 다음과 같습니다.

49
0.1111111111111111
HELLO WORLD
[(3.515625, 39.0625), (33.0625, 4.0), (5.640625, 90.25)]

결론

다중 프로세스에서 Array 클래스를 이용하여 데이터를 동기화하는 방법에 대하여 알아 보았습니다.


참고자료