Computer >> 컴퓨터 >  >> 프로그램 작성 >> Python

Python에서 다중 스레딩을 사용한 소켓 프로그래밍?

<시간/>

멀티스레딩 개념

멀티스레딩은 스레드의 단순한 구현으로 인해 거의 모든 최신 프로그래밍 언어, 특히 파이썬의 핵심 개념입니다.

스레드는 코드의 다른 섹션과 독립적으로 실행할 수 있는 프로그램 내의 하위 프로그램입니다. 스레드는 메모리와 같은 동일한 컨텍스트 공유 프로그램의 실행 가능한 리소스에서 실행됩니다.

단일 프로세스에서 여러 스레드를 동시에 실행하는 것을 멀티스레딩이라고 합니다.

스레드 구현을 위한 Python 멀티스레딩 모듈

프로그램에서 스레드를 구현하기 위해 파이썬은 두 개의 모듈을 제공합니다 -

  • thread(python 2.x의 경우) 또는 _thread(python 3.x의 경우) 모듈
  • 스레딩 모듈

쓰레드 모듈은 쓰레드를 함수로 생성하는 반면 쓰레드 모듈은 쓰레드 생성을 위한 객체 지향 접근 방식을 제공합니다.

구문

_thread.start_new_thread(func, args[, kwargs])

위는 새 스레드를 시작하고 해당 식별자를 반환합니다. 첫 번째 인수는 위치 인수 목록이 있는 튜플을 포함하는 두 번째 인수로 스레드가 실행하는 함수 func입니다. 선택적 kwargs 인수는 키워드 인수의 사전을 지정합니다. 함수가 반환되면 스레드가 조용히 존재합니다.

여기에서 클라이언트-서버 응용 프로그램의 기본 예를 봅니다. 클라이언트가 기본적으로 소켓 연결을 열고 서버에 쿼리를 보내는 곳. 서버가 응답합니다.

인수 없이 실행할 때 이 프로그램은 포트 8000에서 127.0.0.1에 대한 연결을 수신 대기하는 TCP 소켓 서버로 시작합니다.

client_thread1.py

 import socketimport sysdef main():soc =socket.socket(socket.AF_INET, socket.SOCK_STREAM) 호스트 ="127.0.0.1" 포트 =8000 시도:soc.connect((호스트, 포트)) 제외:print( "연결 오류") sys.exit() print("종료하려면 '종료'를 입력하세요.") message =input(" -> ") while message !='quit':soc.sendall(message.encode("utf8") )) if soc.recv(5120).decode("utf8") =="-":pass # null 연산 메시지 =input(" -> ") soc.send(b'--quit--')if __name__ =="__main__":메인()

반면 서버 프로그램은

server_thread1.py

 import socketimport sysimport tracebackfrom threading import Threaddef main():start_server()def start_server():host ="127.0.0.1" port =8000 # 임의의 비특권 포트 soc =socket.socket(socket.AF_INET, socket. SOCK_STREAM) soc.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) print("소켓 생성") 시도:soc.bind((호스트, 포트)) 예외:print("바인드 실패. 오류:" + str(sys .exc_info())) sys.exit() soc.listen(6) # 최대 6개의 요청을 대기열에 넣습니다. print("Socket now Listening") # 무한 루프 - 모든 요청에 ​​대해 재설정하지 않고 True:연결, 주소 =soc. accept() ip, 포트 =str(주소[0]), str(주소[1]) print("연결된 " + ip + ":" + 포트) try:Thread(target=client_thread, args=(connection, ip, port)).start() 제외:print("스레드가 시작되지 않았습니다.") traceback.print_exc() soc.close()def clientThread(connection, ip, port, max_buffer_size =5120):is_active =True인 동안 is_active :클라이 nt_input =receive_input(connection, max_buffer_size) if "--QUIT--" in client_input:print("클라이언트가 종료 요청 중") connection.close() print("연결 " + ip + ":" + 포트 + " 닫힘 ") is_active =False else:print("처리된 결과:{}".format(client_input)) connection.sendall("-".encode("utf8"))def receive_input(connection, max_buffer_size):client_input =connection.recv (max_buffer_size) client_input_size =sys.getsizeof(client_input) if client_input_size> max_buffer_size:print("입력 크기가 예상보다 큽니다.".format(client_input_size)) decoded_input =client_input.decode("utf8").rstrip() 결과 =process_input(decoded_input) return resultdef process_input(input_str):print("클라이언트로부터 받은 입력 처리") return "Hello" + str(input_str).upper()if __name__ =="__main__":main()

위의 스크립트를 실행할 때 터미널에서 server_thread1.py를 다음과 같이 실행하십시오.

python server_thread1.pySocket createdSocket이 수신 대기 중

서버 창을 보고 흐름을 이해하겠습니다. 이제 여러 클라이언트 터미널을 열고 클라이언트 스레드를 실행합니다.

python client_thread1.py종료하려면 '종료' 입력-> Zack->

다른 터미널에서 다른 클라이언트 프로그램을 실행하고 서버 터미널 창도 보고,

python client_thread1.py종료하려면 'quit'를 입력-> Python-> 종료

다른 터미널, 클라이언트 스레드 실행,

python client_thread1.py종료하려면 '종료'를 입력하세요-> 세상!-> Anothny->

그리고 서버 창에 다음과 같은 출력이 표시되는 것을 볼 수 있습니다.

소켓이 생성됨 이제 127.0.0.1:50275 클라이언트로부터 수신된 입력을 수신하고 있는 소켓이 생성됨 50282 127.0.0.1:50285 클라이언트로부터 받은 입력을 처리하는 중입니다. 

따라서 스레드는 다중 소켓 연결 및 클라이언트를 처리하는 가장 일반적인 기술 중 하나를 제공합니다.