網路通訊中,Socket是應用層與運輸層中間的軟體抽象層,它是一組介面。在設計模式中,Socket其實就是一個門面模式,它把複雜的TCP/IP協議族隱藏在Socket介面後面,對使用者來說,一組簡單的介面就是全部,讓Socket去組織資料,以符合指定的協議。
下文出現的一些套接字屬性:
s.bind() 繫結地址到套接字
s.listen() 開始TCP監聽
s.accept() 被動接受TCP客戶的連線
c.connect() 客戶端主動初始化TCP伺服器連線
s.recv() 接收TCP資料
s.send() 傳送TCP資料
s.recvfrom() 接收UDP資料
s.sendto() 傳送UDP資料
s.close() 關閉套接字
TCP 協議的伺服器:
import socket
server = socket.socket() #使用TCP可以直接預設
ip = '127.0.0.1' #伺服器的IP地址
port = 60000 #埠0-1023是系統保留的
address = (ip,port) #ip和port組成的地址
server.bind(address) #伺服器此繫結地址
server.listen(5) #開始監聽,設定最大半連線數為5
while True:
c,addr = server.accept() #接受連線請求
while True:
try:
#接受資料#
data = c.recv(1024).decode("utf-8") #接收資料並解碼,1024為程式最大緩衝區容量
if not data:
print("client closed!")
c.close()
break
print(data)
#回覆資料並將原始資料轉為大寫#
c.send(data.upper().encode("utf-8")) #轉換完大寫後進行編碼
except ConnectionResetError: #保證伺服器不會因客戶端異常關閉而報錯
print("客戶端異常關閉!!")
c.close()
break
pass
複製程式碼
TCP 協議的客戶端:
import socket
client = socket.socket()
ip = '127.0.0.1'
port = 60000
address = (ip,port)
client.connect(address) #建立客戶端與伺服器的連線
while True:
msg = input('<q.退出>>>:') #等待輸入資料
if not msg:
continue
if msg == 'q': #輸入q時退出
c.close()
break
#傳送資料#
client.send(msg.encode('utf-8'))
#接受資料#
data = client.recv(1024).decode('utf-8')
print(data)
複製程式碼
UDP協議的伺服器:
import socket
# 建立socket物件,指定type引數為socket.SOCK_DGRAM 表示使用UDP協議
server = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)
ip = '127.0.0.1'
port = 8888
address = (ip,port)
server.bind(address) # 繫結ip和埠
while True:
#接收#
msg,addr = server.recvfrom(1024)
print("收到來自%s: 說:%s" % (addr[0] ,msg.decode("utf-8")))
#傳送#
server.sendto(msg.upper(),addr) #傳送接收訊息的大寫給原地址
複製程式碼
UDP協議的客戶端:
import socket
client = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) # datagram資料包的意思
ip = '127.0.0.1'
port = 8888
address = (ip,port) #伺服器地址
while True:
msg = input(">>>:") #輸入資訊
client.sendto(msg.encode("utf-8"),address) #sendto需要給伺服器地址
data,addr = client.recvfrom(1024) #recvfrom接收資料和地址
print(data.decode("utf-8"))
複製程式碼
UDP與TCP的區別: 不需要監聽,不需要接收,type引數為 SOCK_DGRAM。 UDP 可以同時處理多個客戶端,TCP有半連線池的概念。