首頁 > 軟體

Python Socket 程式設計知識點詳細介紹

2022-02-22 13:01:13

前言:

    Socket又稱為通訊端,它是所有網路通訊的基礎。網路通訊其實就是程序間的通訊,Socket主要是使用IP地址,協定,埠號來標識一個程序。埠號的範圍為0~65535(使用者埠號一般大於1024),協定有很多種,一般我們經常用到的就是TCP,IP,UDP。下面我們來詳細瞭解下Socket吧。

一、匯入Socket模組

因為要操作通訊端,所以需要用到通訊端模組,系統中自帶的就很不錯,下面我們來匯入:

import socket

二、Socket基本用法

1.建立一個簡單的Socket連線

#建立Tcp/Ip通訊端
s=socket.socket(socket.AF_INET,socket.SOCK_STREAM) #流式Socket
#建立Udp/Ip通訊端
s=socket.socket(socket.AF_INET,socket.SOCK_DGRAM) #資料包式Socket
socket.AF_UNIX  #只能夠用於單一的Unix系統程序間通訊
socket.AF_INET6  #只能夠用於IPv6通訊
socket.SOCK_RAW  #原始通訊端,可以處理ICMP、ARP等網路報文,其它的不行
socket.SOCK_SEQPACKET  #可靠的連續封包服務

2.協定對應埠

應用程式    FTP   TFTP  TELNET  SMTP  DNS   HTTP  SSH   MYSQL  POP3   MONGO
  埠     21,20  69     23     25    53    80    22    3306   110   27017
  協定      TCP   UDP    TCP    TCP   UDP   TCP   TCP    TCP   TCP    TCP

3.Socket函數

#建立Socket連線,比Connect更高階,可以自動解析不是數位的host地址,相容IPv4和 IPv6
socket.create_connection(address=('localhost',4320),timeout=4,source_address=('localhost',4320))  #前後兩個埠號一定要是一致,不然會報錯


#構建一對已連線的通訊端物件,新建立的通訊端都是不可繼承的
socket.socketpair(family=socket.AF_INET,type=socket.SOCK_STREAM,proto=0)


#從檔案描述符獲取到socket連線物件
socket.fromfd(fd=ab.fileno(),family=socket.AF_INET,type=socket.SOCK_STREAM,proto=0)


#通訊端物件的型別
socket.SocketType


#返回通訊端的5元組列表地址 ,支援IPV4/IPV6解析
socket.getaddrinfo(host='localhost',port=3453,family=socket.AF_INET,type=socket.SOCK_STREAM,proto=socket.IPPROTO_TCP,flags=0)
output:
[(<AddressFamily.AF_INET: 2>, <SocketKind.SOCK_STREAM: 1>, 6, '', ('127.0.0.1', 3453))]


#獲取主機名
socket.gethostname()
socket.getfqdn()
socket.getfqdn(socket.gethostname())


#將主機名轉化為IP地址
socket.gethostbyname('www.baidu.com') #不支援IPV6解析
socket.gethostbyname_ex('www.baidu.com') #返回三元組,(主機名,相同地址的其它可用主機名的列表,IPv4 地址列表)


#網路ip地址
socket.gethostbyname(socket.getfqdn(socket.gethostname()))


#將ip地址轉化為主機名,返回三元組(主機名,相同地址的其它可用主機名的列表,IPv4地址列表),支援IPV4/IPV6
socket.gethostbyaddr('192.168.1.4')


#解析主機名或者IP地址
socket.getnameinfo(('192.168.1.4',5434),0)


#判斷是否支援IPV6
socket.has_ipv6


#返回服務所使用的埠號
socket.getservbyname('https','tcp') #第一個引數為服務協定:Https,Http;第二個為傳輸協定:Tcp Udp


#返回埠所對應的服務
socket.getservbyport(443,'tcp')


#設定主機名(僅限於Unix)
socket.sethostname(name)


#返回網路卡資訊的列表(僅限於Unix)
socket.if_nameindex()


#32位元位元組儲存Ip地址(序列化)
socket.inet_aton('127.0.0.1')


#將32位元位元組轉化為Ip地址(反序列化)
socket.inet_ntoa(b'x7fx00x00x01')

4.通訊端函數

1).伺服器端函數

s.bind((host,port)) #將地址繫結到通訊端,以(host,port)的元祖形式
s.listen(num)  #建立最多num個連線,最好別太大
s.accept()     #等待並接受使用者端的連線,返回新的通訊端物件和(host,port)元祖

2).使用者端函數

s.connect((host,port)) #建立與伺服器的連線,以(host,port)的元祖形式
s.connect_ex((host,port)) #和上面的功能差不多,只是出錯了不拋異常,只是返回出錯碼

3).通用函數

s.recv(size,flag)       #接收最多size個大小的資料,flag可以忽略,返回值為資料是字串形式
s.send(str,flag)        #傳送str資料,返回值是要傳送的位元組數量,可能資料未全部傳送
s.sendall(str,flag)     #傳送全部str資料,成功返回None,失敗則丟擲異常
s.recv(size,flag)       #接受最多size個資料,並以字串形式返回
s.recvfrom(str,flag)    #與recv相同,但是返回值是(接收資料的字串,傳送資料的通訊端地址)的元祖形式
s.sendto(str,flag,address) #連線到當前通訊端的遠端地址。返回值是傳送的位元組數,主要用於UDP
s.getpeername()     #返回連線通訊端的遠端地址。返回值通常是元組(host,port)
s.getsockname()     #返回通訊端自己的地址。通常是一個元組(host,port)
s.setsockopt(level,optname,value) # 設定給定通訊端選項的值。
#假如埠被socket使用過,並且利用socket.close()來關閉連線,但此時埠還沒有釋放,要經過TIME_WAIT的過程之後才能使用;為了實現埠的馬上覆用,可以選擇setsocket()函數來達到目的。
#level:選項定義的層次。支援SOL_SOCKET、IPPROTO_TCP、IPPROTO_IP和IPPROTO_IPV6。
#optname:需設定的選項。SO_REUSEADDR SO_REUSEPORT
#value:設定選項的值。
s.getsockopt(level,optname,buflen) #返回通訊端選項的值。buflen:快取長度
s.settimeout(time)  #設定socket連線超時時間,單位為秒,超時一般在剛建立通訊端時設定
s.gettimeout()      #返回當前超時的時間,單位是秒,如果沒有設定超時,則返回None。
s.close()           #關閉通訊端
s.fileno()          #通訊端的檔案描述符
s.shutdown(how)     # 關閉連線一邊或兩邊
s.setblocking(bool) #是否阻塞(預設True),如果設定False,那麼accept和recv時一旦無資料,則報錯。
s.makefile()        #建立一個與該通訊端相關聯的檔案

5.一個簡單的使用者端與伺服器端互動

Server.py

import socket 
s=socket.socket(socket.AF_INET, socket.SOCK_STREAM)             # 建立socket物件
s.bind(('127.0.0.1',4323))                                      # 繫結地址
s.listen(5)                                                     # 建立5個監聽
while True:
    conn,addr= s.accept()                                       # 等待使用者端連線
    print('歡迎{}'.format(addr))                              #列印存取的使用者資訊
    while True:
        data=conn.recv(1024) 
        dt=data.decode('utf-8')                                 #接收一個1024位元組的資料 
        print('收到:',dt)
        aa=input('伺服器發出:') 
        if aa=='quit':
            conn.close()                                        #關閉來自使用者端的連線
            s.close()                                           #關閉伺服器端連線
        else:
            conn.send(aa.encode('utf-8'))                       #傳送資料

Client.py

import socket   
import sys
c=socket.socket()                                           # 建立socket物件
c.connect(('127.0.0.1',4323))                                #建立連線
while True:
    ab=input('使用者端發出:')
    if ab=='quit':
        c.close()                                               #關閉使用者端連線
        sys.exit(0)
    else:
        c.send(ab.encode('utf-8'))                               #傳送資料
        data=c.recv(1024)                                        #接收一個1024位元組的資料
        print('收到:',data.decode('utf-8'))                    #輸出接收的資訊

可以看到我們實現了一個全雙工的Tcp/Ip聊天工具,對於伺服器和使用者端來說,均可收發檔案。

三、總結

    Python中的socket程式設計難度不大,不過你要想寫好的Socket也不容易,希望本文能讓大家受益匪淺,畢竟小編可是把絕大多數經常用到的Api的功能都展示了。

到此這篇關於Python Socket 程式設計知識點詳細介紹的文章就介紹到這了,更多相關Python Socket 程式設計內容請搜尋it145.com以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援it145.com!


IT145.com E-mail:sddin#qq.com