具有多个线程的Python套接字编程

时间:2014-11-30 21:22:57

标签: python multithreading sockets network-programming

我正在尝试在python中使用套接字。现在,我试图得到它,如果任何客户端发送任何消息,它将在所有客户端收到。但是我得到了非常奇怪的结果。我认为这是因为我使用多个线程。每次运行程序时,程序的输出都会改变。这是一个线程问题还是别的什么?

import socket
import sys
from thread import *
from server import Server
from client import Client

s = Server()
start_new_thread(s.acceptConnection,())


m = Client("m")
k = Client("k")
start_new_thread(m.recieveData,())
start_new_thread(k.recieveData,())
k.sendData("Hey!")
print "*"*100
print repr(k.data()), repr(m.data())
print "*"*100
m.sendData("okay okay")
print "*"*100
print repr(k.data()), repr(m.data())
print "*"*100
m.client.close()
k.client.close()
s.s.close()

服务器类:

import socket
import sys
from thread import *

class Server(object):
    def __init__(self,port = 5555):
        self.host = 'localhost'  # '' means connect to all hosts
        self.port = port
        self.text = ""        
        self.s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        self.s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
        try:
            self.s.bind((self.host, self.port))
        except socket.error as e:
            print(str(e))
        self.s.listen(2)
        print "Waiting for a connection.\n"
        self.connections = []

    def threaded_client(self,conn):
        # conn.send("Connected to server\n")
        while True:
            try:
                data = conn.recv(2048)
            except:
                data = ""
            if(not data):
                break
            # conn.sendall(reply)
            for c,a in self.connections:
                try:
                    c.sendall(data + "\n")
                except:
                    print "connection lost\n"
                    self.connections.remove((c,a))
        conn.close()

    def acceptConnection(self):
        while True:
            conn, addr = self.s.accept()
            self.connections += [(conn,addr)]
            start_new_thread(self.threaded_client,(conn,))

客户端类:

import socket
import sys
from thread import *

class Client(object):
    def __init__(self,name):
        self.host = 'localhost'
        self.port = 5555
        self.name = name
        self.client= socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
        self.client.connect((self.host,self.port))
        self.text = ""

    def sendData(self,data):
        self.client.send(data)

    def recieveData(self):
        while True:
            try:
                data = self.client.recv(2048)
            except:
                break
            if data:
                self.text = data
        self.client.close()

    def data(self):
        return self.text

    def closeClient(self):
        self.client.close()

1 个答案:

答案 0 :(得分:0)

无论如何,当您尝试打印时,您没有关于数据已经回到客户端的保证。您应该介绍一些Conditions并使用wait()notifyAll()来确保数据到达....要检查我的猜测是否正确,请在测试中添加一些sleep()

import time
k.sendData("Hey!")
print "*"*100
time.sleep(200)
print repr(k.data()), repr(m.data())
print "*"*100
m.sendData("okay okay")
print "*"*100
time.sleep(200)
print repr(k.data()), repr(m.data())
print "*"*100

如果有效,您应该使用条件并通知您进行测试。

此外,您必须通过data保护Lock()访问权限。

def recieveData(self):

    while True:
        try:
            data = self.client.recv(2048)
        except:
            break
        if data:
            self.l.acquire()
            self.text = data
            self.l.release()
    self.client.close()

def data(self):
    self.l.acquire()
    ret = self.text
    self.l.release()
    return ret

客户的属性l__init__中由

定义
self.l=threading.Lock()