2015-12-03 90 views
0

我正在学习如何使用线程和套接字连接。 我在网上找到了有关线程和套接字连接如何工作的文献和示例。现在我试图将两者合并在一起来创建一个简单的发送/接收应用程序。所以这是我放在一起作为一个例子:Python - 错误:[Errno 111]连接被拒绝并且错误:[Errno 98]地址已被使用

main.py,

import server 
import client 
import threading 

def main(): 
    try: 
     threadA = threading.Thread(target=server.serv) 
     threadA.start() 

     threadB = threading.Thread(target=client.client) 
     threadB.start() 
    except: 
     print "Got an Error" 

if __name__ == '__main__': 
    main() 

server.py

#!/usr/bin/python   # This is server.py file 

import socket    # Import socket module 

def serv(): 
    s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)   # Create a socket object 
host = socket.gethostname() # Get local machine name 
port = 12920    # Reserve a port for your service. 
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) 

s.bind((host, port))  # Bind to the port 

s.listen(5)     # Now wait for client connection. 
#while True: 
c, addr = s.accept()  # Establish connection with client. 
print 'Got connection from', addr 
c.send('Thank you for connecting') 
s.shutdown(1) 
c.close()    # Close the connection 

client.py

#!/usr/bin/python   # This is client.py file 

import socket    # Import socket module 

def client(): 
    s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)   # Create a socket object 
    s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) 
    host = socket.gethostname() # Get local machine name 
    port = 12920    # Reserve a port for your service. 

    s.connect((host, port)) 
    print s.recv(1024) 
    s.shutdown(1) 
    s.close      # Close the socket when done 

我能够在没有任何运行首次应用错误。下面是输出:从 GOT连接(“172.17.132.98”,50759)
感谢您连接

当我再次运行应用程序(第二次连续的),我收到以下错误:

Traceback (most recent call last):                                 
File "/usr/lib64/python2.7/threading.py", line 813, in __bootstrap_inner                       
     self.run()                                      
File "/usr/lib64/python2.7/threading.py", line 766, in run                          
    self.__target(*self.__args, **self.__kwargs)                             
File "/home/cg/root/client.py", line 12, in client                            
    s.connect((host, port))                                   
File "/usr/lib64/python2.7/socket.py", line 228, in meth                           
    return getattr(self._sock,name)(*args)                               
error: [Errno 111] Connection refused 

在这里,我点击ctrl + Z键停止挂起的应用程序。

如果我尝试再次运行该应用程序,我收到以下错误:螺纹加工-1 异常:

Traceback (most recent call last):                                 
    File "/usr/lib64/python2.7/threading.py", line 813, in __bootstrap_inner                       
    self.run()                                      
    File "/usr/lib64/python2.7/threading.py", line 766, in run                          
    self.__target(*self.__args, **self.__kwargs)                             
    File "/home/cg/root/server.py", line 11, in serv                             
    s.bind((host, port))  # Bind to the port                             
    File "/usr/lib64/python2.7/socket.py", line 228, in meth                           
    return getattr(self._sock,name)(*args)                               
error: [Errno 98] Address already in use 

有人能告诉我什么,我做错了什么?

Thanks InAdvance

+0

ctrl + Z在后台暂停进程,因此套接字仍然被绑定,因此“地址已被使用” –

+0

但是为什么在第一次运行应用程序后出现以下错误: :[Errno 111]连接被拒绝 我希望能够在没有遇到任何问题的情况下重复执行此操作。 – linos

+0

在套接字关闭后,您应该捕获KeyBoardInterrupt并终止服务器 –

回答

2

您的客户端代码并未真正关闭连接。您的代码有以下几点:

s.close 

这应该是:

s.close() 

因此,你要离开的连接在服务器上打开和资源没有得到正确释放。这就是为什么你得到了地址在使用中的错误。该港口仍然受到约束并“正在使用”。此外,如果您使用“Ctrl + Z”暂停应用程序,它仍在后台执行,并且资源尚未释放。您需要实际终止进程以释放资源。

+0

,是否需要等待一段时间才能创建新的套接字以使用相同的端口并传输数据?我发现重新运行相同的应用程序会导致不可重复的结果。有时它会起作用,有时会失败。 – linos

0

Here I hit the ctrl+Z key to halt the hung application.

这是你的问题。要停止一个应用程序,你必须按ctrl + c;与ctrl + z你只需将其发送到背景。该应用程序仍处于打开状态,并使用相同的地址和端口。

如果您向后台发送应用程序,您可以将它带回fg,使其在bg的后台保持运行或使用kill %1将其终止。杀死它(或将它带回前台并用ctrl + c停止它)应该释放资源。

0

我发现我的例子中,启动threadA和threadB之间有一个时间问题。服务器和客户端之间的竞争条件。所以我添加了一个线程。在它们之间休眠(1)并没有遇到我以前遇到的假错误。

谢谢大家的帮助。我更多地了解了线程和套接字如何协同工作。

相关问题