python3 下的Socket编程(TCP&UDP )

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/ykiwmy/article/details/78768970

网络编程中最重要的两个协议:TCP协议和UDP协议

TCP协议是互联网中使用最广泛的传输协议,这得益于其稳定,可靠的优势。TCP协议是面向连接的传输协议,通信双方(通常是两个主机上面的两个程序)需要先建立连接,才能传输数据。数据在传输过程中会被分成多个小的数据包,这些数据包都会被添加上序号,全部达到接收端的小数据包会根据这些序号重新拼凑起来。TCP传输的数据包加入了检验码,可以检测在传输过程中数据包是否被更改过,对于更改过或者损失了数据的数据包,接收端会要求发送端重新发送。接收端在收到发送端发送的数据包之后,会回送一个消息到发送端,告诉发送端已经安全接收到数据包了,如果发送端没有收到这个回送消息,则会经过一段时间再次发送该数据包。因此在这种协议下面,数据的传输是十分稳定可靠的。

UDP协议是一类无连接的传输协议。发送端只管将数据发送出去,接收端收到数据后也不会发送回送消息给发送端,因此发送端并不知道接收端有没有收到完整的数据。TCP需要的时间和系统开销都比UDP大,UDP在传输一些小数据时有一定的优势,通常来说UDP一次传输的数据大小不能超过64kb,一般来说最佳的数据大小是<1kb。

python3可以使用socket模块简单的实现TCP与UDP传输协议,下面看服务器和客户端代码

TCP传输的python3代码:

 
 
#服务器端代码++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
#/usr/bin/env python
import  socket
import  time
host = ''
port = 51423
bufsize = 1024
addr = ( host , port ) #host设定为空,表示可以与任何ip的socket在端口51423通信
#设置socket,AF_INET表示是IPV4标准,SOCK_STREAM是TCP传输协议
tcpSerSock = socket . socket ( socket . AF_INET , socket . SOCK_STREAM )
tcpSerSock . bind ( addr )
tcpSerSock . listen ( 1 )
quit = False
shutdown = False
while  True :
print ( 'waiting for connection...' )
tcpCliSock , addr = tcpSerSock . accept () #不断监听获取新的客户端连接
print ( '...connected from:' , addr )
while  True : #与客户端建立连接之后,获取客户端传来的数据
data = tcpCliSock . recv ( bufsize )
data = data . decode ( 'utf-8' )
if  not  data :
break
ss = '[ %s %s ' % ( time . ctime (), data )
tcpCliSock . sendall ( ss . encode ( 'utf-8' ))
print ( ss )
if  data == 'bye' :
quit = True
break
elif  data == 'shutdown' :
shutdown = True
break
print ( 'Bye-bye:[ %s : %d ]' % ( addr [ 0 ], addr [ 1 ]))
tcpCliSock . close ()
if  shutdown :
break
tcpSerSock . close ()
print ( 'Server has been closed' )
#客户端代码+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
import  socket
host = '192.168.1.147'
port = 51423
bufsize = 1024
addr = ( host , port )
tcpCliSock = socket . socket ( socket . AF_INET , socket . SOCK_STREAM )
tcpCliSock . connect ( addr )
while  True :
data = input ( '>' )
if  not  data :
continue
print ( 'input data:[ %s ]'  % data )
tcpCliSock . sendall ( data . encode ( 'utf-8' ))
rdata = tcpCliSock . recv ( bufsize )
if  not  rdata :
break
print ( rdata . decode ( 'utf-8' ))
if  data == 'bye'  or  data == 'shutdown' :
break
首先启动服务器代码,然后在启动客户端代码,这样服务器与客户端就建立了连接。在客户端控制台输入的数据会在服务器控制台显示出来。客户端输入'bye'字符时,服务器会关闭客户端的socket连接,客户端输入'shutdown'时,服务器关闭客户端和服务器端的socket连接。

测试代码时最好能用两台电脑测试。也可以像博主一样在一台电脑上面装一个虚拟机操作系统,使用桥接模式,也可以模拟客户端和服务器端完成端到端测试。

UDP传输的python代码:

#服务器端++++++++++++++++++++++++++++++++++++++++++++++++

import socket

BUFF_SIZE = 1024
server_addr = ('127.0.0.1', 55555)

s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)            # SOCK_DGRAM是UDP传输协议
s.bind(server_addr)
print('bind ok!')

while True:
    data, addr = s.recvfrom(BUFF_SIZE)
    print(data)
    if data is 'bye':
        print('client has exit')
        break
    print('received:', data, " from", addr)
s.close()


#客户端+++++++++++++++++++++++++++++++++++++++++++++++++++++

import socket

server_addr = ('127.0.0.1', 55555)
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
while True:
    msg = input('>')
    print(msg)
    s.sendto(msg.encode('utf-8'), server_addr)
    if msg is 'bye':
        break
s.close()

UDP由于是无连接的传输协议,因此这里创建的socket对象不需要调用connnect()方法建立连接,可以直接使用sendto()和recvfrom()来发送和接收数据。UDP协议并不可靠,发送端不知道接受端有没有收到数据,发送端就只在发送的时候发送一次数据,如果网络拥塞很有可能造成接收端没有正常接收到数据。TCP连接会多次重发数据,直到接收到来自接收方的回送消息为止。


猜你喜欢

转载自blog.csdn.net/ykiwmy/article/details/78768970