[파이썬] PyQt 비동기 프로그래밍 (`QFuture`, `QFutureWatcher`)

PyQt는 Python에서 사용할 수 있는 강력한 GUI 프레임워크입니다. PyQt를 사용하여 다양한 어플리케이션을 개발할 수 있지만, 때때로 어플리케이션의 성능을 향상시키기 위해 비동기 프로그래밍이 필요할 수 있습니다. PyQt에서 비동기 프로그래밍을 구현하기 위해 QFutureQFutureWatcher 클래스를 사용할 수 있습니다.

QFuture

QFuture 클래스는 비동기 작업의 결과를 표현하는 클래스입니다. 이 클래스는 asyncio와 같은 비동기 패턴을 편리하게 사용할 수 있도록 도와줍니다. 예를 들어, 파일 다운로드나 네트워크 요청과 같은 시간이 오래 걸리는 작업을 처리할 때 유용합니다.

아래는 QFuture를 사용하여 간단한 예시를 보여주는 코드입니다.

import sys
from PyQt5.QtCore import QFuture, Qt, QThreadPool
from PyQt5.QtWidgets import QApplication, QLabel

def long_running_task():
    # 시간이 오래 걸리는 작업을 수행하는 함수
    # 예를 들어, 파일 다운로드

    # 결과를 반환
    return "작업 완료"

app = QApplication(sys.argv)

# QThread를 사용하여 작업을 실행
thread_pool = QThreadPool.globalInstance()

# 결과를 나타내는 QFuture 생성
future = QFuture(long_running_task)

# QThreadPool을 사용하여 작업 실행
thread_pool.start(future)

# 메인 윈도우 생성
window = QLabel("작업 중...")
window.setAlignment(Qt.AlignCenter)
window.show()

# 작업이 완료되면 결과를 업데이트
future.resultReadyAt.connect(lambda index: window.setText(future.result()))

sys.exit(app.exec_())

QFutureWatcher

QFutureWatcher 클래스는 QFuture의 진행 상태를 모니터링하는 데 사용됩니다. 이 클래스는 작업이 완료되었을 때 결과를 처리하는 데 유용합니다. 또한 QFuture 대신 QFutureWatcher를 사용하여 작업의 진행 상태에 따라 UI를 업데이트하는 등의 추가 작업을 수행할 수 있습니다.

아래는 QFutureWatcher를 사용한 예시 코드입니다.

import sys
from PyQt5.QtCore import QFuture, Qt, QThreadPool, QFutureWatcher
from PyQt5.QtWidgets import QApplication, QLabel

def long_running_task():
    # 시간이 오래 걸리는 작업을 수행하는 함수
    # 예를 들어, 파일 다운로드

    # 결과를 반환
    return "작업 완료"

def on_finished():
    # 작업이 완료되면 호출되는 콜백 함수
    result = future.result()  # 결과 가져오기
    window.setText(result)   # 결과 업데이트

app = QApplication(sys.argv)

# QThread를 사용하여 작업을 실행
thread_pool = QThreadPool.globalInstance()

# 결과를 나타내는 QFuture 생성
future = QFuture(long_running_task)

# QThreadPool을 사용하여 작업 실행
thread_pool.start(future)

# 메인 윈도우 생성
window = QLabel("작업 중...")
window.setAlignment(Qt.AlignCenter)
window.show()

# 작업이 완료되면 결과를 처리하기 위한 QFutureWatcher 생성
watcher = QFutureWatcher()
watcher.setFuture(future)

# 작업이 완료되었을 때 호출할 콜백 함수 연결
watcher.finished.connect(on_finished)

sys.exit(app.exec_())

결론

PyQt를 사용하여 비동기 작업을 처리하는 것은 매우 유용합니다. QFutureQFutureWatcher 클래스를 사용하면 보다 효율적인 GUI 프로그래밍을 구현할 수 있습니다. 위의 코드 예시를 참고하여 PyQt에 비동기 프로그래밍을 적용해 보세요.