參考來源(其實我從上面復制了一點):
Python?的?Socket?編程教程??http://www.oschina.net/question/12_76126
Python線程指南?http://www.open-open.com/lib/view/open1345476194313.html
Python?的?Socket?編程教程??http://www.oschina.net/question/12_76126
Python線程指南?http://www.open-open.com/lib/view/open1345476194313.html
Python Socket文檔?https://docs.python.org/3/library/socket.html#socket-objects
具體思路:
每個client有兩個線程,分別負責接收和發送,當沒有發送時,在raw_input()那卡住,當沒有接收時,在recv()那卡住
server為每個client開兩個線程,分別處理接收和發送。每個發送的線程在con.wait()那阻塞,等待notify。每個接收的線程,在recv()那里等待來自client的輸入,接收到輸入后,發出一個notify,激活所有輸出線程,自身則因為循環在下一個recv()那里等待。
這樣做的優勢時在等待期間,cpu都處于空閑狀態,cpu只在接收和發送的瞬間被使用。
目前沒有想到更好方法。。。
注意:
我做得有點粗糙,復制后有些注釋和代碼對應不起來,也沒有添加新的注釋
具體思路:
每個client有兩個線程,分別負責接收和發送,當沒有發送時,在raw_input()那卡住,當沒有接收時,在recv()那卡住
server為每個client開兩個線程,分別處理接收和發送。每個發送的線程在con.wait()那阻塞,等待notify。每個接收的線程,在recv()那里等待來自client的輸入,接收到輸入后,發出一個notify,激活所有輸出線程,自身則因為循環在下一個recv()那里等待。
這樣做的優勢時在等待期間,cpu都處于空閑狀態,cpu只在接收和發送的瞬間被使用。
目前沒有想到更好方法。。。
注意:
我做得有點粗糙,復制后有些注釋和代碼對應不起來,也沒有添加新的注釋
標簽:?<無>
代碼片段(4)[全屏查看所有代碼]
1.?[文件]?client.py?~?976B?????下載(283)?????
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 | # -*- coding: utf-8 -*- """ Created on Thu Oct 24 17:35:50 2013 @author: zbg """ import socket import threading inString = '' outString = '' nick = '' def DealOut(s): ???? global nick, outString ???? while True : ???????? outString = raw_input () ???????? outString = nick + ': ' + outString ???????? s.send(outString) def DealIn(s): ???? global inString ???? while True : ???????? try : ???????????? inString = s.recv( 1024 ) ???????????? if not inString: ???????????????? break ???????????? if outString ! = inString: ???????????????? print inString ???????? except : ???????????? break ???????? ?nick = raw_input ( "input your nickname: " ) ip = raw_input ( "input the server's ip adrress: " ) sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) sock.connect((ip, 8888 )) sock.send(nick) thin = threading.Thread(target = DealIn, args = (sock,)) thin.start() thout = threading.Thread(target = DealOut, args = (sock,)) thout.start() #sock.close() |
2.?[文件]?server.py?~?2KB?????下載(285)?????
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 | # -*- coding: utf-8 -*- """ Created on Fri Oct 25 10:33:44 2013 @author: zbg """ import socket import sys import threading con = threading.Condition() HOST = raw_input ( "input the server's ip adrress: " ) # Symbolic name meaning all available interfaces PORT = 8888 # Arbitrary non-privileged port data = '' s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) print 'Socket created' s.bind((HOST, PORT)) s.listen( 10 ) print 'Socket now listening' #Function for handling connections. This will be used to create threads def clientThreadIn(conn, nick): ???? global data #infinite loop so that function do not terminate and thread do not end. ???? while True : ???? #Receiving from client ???????? try : ???????????? temp = conn.recv( 1024 ) ???????????? if not temp: ???????????????? conn.close() ???????????????? return ???????????? NotifyAll(temp) ???????????? print data ???????? except : ???????????? NotifyAll(nick + " leaves the room!" ) ???????????? print data ???????????? return ???? #came out of loop def NotifyAll(sss): ???? global data ???? if con.acquire(): ???????? data = sss ???????? con.notifyAll() ???????? con.release() ? ?def ClientThreadOut(conn, nick): ???? global data ???? while True : ???????? if con.acquire(): ???????????? con.wait() ???????????? if data: ???????????????? try : ???????????????????? conn.send(data) ???????????????????? con.release() ???????????????? except : ???????????????????? con.release() ???????????????????? return ???????????????????? ?while 1 : ???? #wait to accept a connection - blocking call ???? conn, addr = s.accept() ???? print 'Connected with ' + addr[ 0 ] + ':' + str (addr[ 1 ]) ???? nick = conn.recv( 1024 ) ????? #send only takes string ???? #start new thread takes 1st argument as a function name to be run, second is the tuple of arguments to the function. ???? NotifyAll( 'Welcome ' + nick + ' to the room!' ) ???? print data ???? print str ((threading.activeCount() + 1 ) / 2 ) + ' person(s)!' ???? conn.send(data) ???? threading.Thread(target = clientThreadIn , args = (conn, nick)).start() ???? threading.Thread(target = ClientThreadOut , args = (conn, nick)).start() s.close() |