python網絡編程udp(基礎篇十一)

一 網絡編程udp

1 計算機網絡概述

計算機網絡, 是指將地理位置不同的具有獨立功能的多臺計算機及其外部設備, 通過通信線路連接起來, 實現資源共享和信息傳遞的計算機系統.

簡言之, 一些相互連接的、以共享資源爲目的、自治的計算機的集合.

思考: 我們現在生活可以離開網絡嗎?

顯然是不可能的, 查詢信息,社交溝通都需要建立在網絡的基礎上. 我們需要編寫基於網絡的程序. 通俗來說就是能夠進行網絡編程, 開發網絡通信程序或者軟件
在這裏插入圖片描述

2 IP地址

<1>IP地址的作用

IP 地址是指互聯網協議地址(英語:Internet Protocol Address,又譯爲網際協議地址), 是 IP Address 的縮寫. IP 地址是 IP 協議提供的一種統一的地址格式.

IP 地址被用來給 Internet 上的電腦一個編號。大家日常見到的情況是每臺聯網的 PC 上都需要有 IP 地址, 才能正常通信。我們可以把 “個人電腦” 比作 “一臺電話”,那麼 “IP地址” 就相當於 “電話號碼”.

IP 地址是標識網絡中唯一的一臺設備. 每個要進行網絡通信的設備, 它的 IP 地址是不一樣的. IP 地址通常表現爲4個數字, 並且數字以點隔開. 每個點隔開的數字都是 0-255 之間.

<2> IP地址的操作

我們可以通過 ifconfig 命令來查看和配置網卡的 IP 地址.

ifconfig查看網卡的信息:

<3> 檢查網絡連通性

  1. ping 127.0.0.1 檢查本機操作系統網絡功能工作是否正常.
  2. ping 本機網卡IP地址 檢查網卡是否正常工作.
  3. ping 遠程主機IP/域名 檢查與遠程主機的連通性

3 端口

<1> 端口作用

端口是操作系統分配給網絡應用程序的編號, 當接收到數據之後, 操作系統會根據編號來將數據轉發到對應編號的應用程序

<2> 端口號

端口號就是標識端口的一個編號. 在 Linux 系統中, 端口號在 0-65535 之間. 端口號不是隨意使用的, 而是按照一定的規定(操作系統規定)進行分配. 端口號分:

  1. 知名端口號.
  2. 動態端口號.

網絡通信的流程先通過 IP 地址找到網絡中的設備, 再通過網絡端口號來找到對應的程序端口, 然後通過端口把數據傳輸給對應的應用程序.

<3> 知名端口

知名端口號是系統程序使用的端口號. 知名端口範圍從 0 到 1023.

  1. 80 端口分配給 HTTP 服務
  2. 22 端口分配給 SSH 服務.
  3. 21 端口分配給 FTP 服務

<4> 動態端口

動態端口號是普通程序使用的端口號. 動態端口的範圍是從 1024 到 65535. 當這個程序關閉時, 同時也就釋放了所佔用的端口號.

<5> 查看端口

  • netstat -an | grep “:8080” 檢驗本機各端口的網絡連接情況.
  • lsof -i [tcp/udp]:8080 列出當前系統端口所對應的程序.

提示: 如果非當前用戶啓動的軟件, 需要添加 sudo 權限

4 UDP傳輸

<1> udp概述

UDP 英文全拼 (User Datagram Protocol) 簡稱用戶數據報協議, 它是無連接的、不可靠的網絡傳輸協議.

UDP 網絡傳輸協議好比現實生活中寫信.

<2> udp的特點

因爲 UDP 發送數據之前不需要建立連接所有具有以下特點:

  1. 無連接
  2. 資源開銷小
  3. 傳輸速度快
  4. udp每個數據包最大是64K

<3> udp的優缺點

  1. 優點:
    • 傳輸速度快
    • 不需要連接,資源開銷小
  2. 缺點:
    • 傳輸數據不可靠,容易丟數據包
    • 沒有流量控制,當對方沒有及時接收數據,發送方一直髮送數據會導致緩衝區數據滿了,電腦出現卡死情況,所有接收方需要及時接收數據。

<4> udp使用場景

當對網絡通訊質量要求不高的時候,要求網絡通訊速度能儘量的快,這時就可以使用UDP.

  • qq音視頻傳輸,微信音視頻傳輸
  • 上課使用的共屏軟件
  • 發送廣播消息

5 socket介紹

<1> 不同電腦進程之間通信

首先通過 IP 地址找到網絡中對應的電腦,然後通過傳輸協議和端口號來確定這個進程(運行起來的軟件),那麼數據如何傳輸需要使用 socket 來完成,也就是進程之間通信使用 socket.

什麼是進程? 什麼是進程間通信?

  1. 所謂進程指的是:運行的程序或者軟件稱之爲進程(在講解多任務編程時進行詳細講解)
  2. 所謂進程間通信指的是:運行的程序之間的數據共享

<2> 什麼是socket

socket(簡稱 套接字) 是進程間通信一個工具,它能實現把數據從一方傳輸到另外一方,完成不同電腦上進程之間的通信, 它好比數據的搬運工。

<3> socket使用場景

不誇張來說,只要跟網絡相關的應用程序或者軟件都使用到了socket, 比如:

6 udp發送和接收數據

<1> UDP 網絡程序流程

創建一個基於 UDP 的網絡程序流程很簡單, 具體步驟如下:

  1. 創建 UDP 套接字
  2. 發送/接收數據
  3. 關閉套接字

img

<2> 創建 socket

在 Python 中 使用socket 模塊的函數 socket 就可以完成:

import socket
socket.socket(AddressFamily, Type)

說明:

函數 socket.socket 創建一個 socket,該函數帶有兩個參數:

Address Family:IP地址類型; AF_INET表示ipv4類型、AF_INET6表示ipv6類型; Type:套接字類型,可以是 SOCK_STREAM(流式套接字,主要用於 TCP 協議)或者 SOCK_DGRAM(數據報套接字,主要用於 UDP 協議)

創建一個udp socket(udp套接字)

import socket

# 創建udp的套接字
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

# ...這裏是使用套接字的功能(省略)...

# 不用的時候,關閉套接字
s.close()

<3> 發送數據

代碼如下:

import socket

# 1. 創建udp套接字
udp_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

# 2. 準備接收方的地址
# '192.168.1.103'表示目的ip地址
# 8080表示目的端口
dest_addr = ('192.168.1.103', 8080)  # 注意 是元組,ip是字符串,端口是數字

# 3. 從鍵盤獲取數據
send_data = input("請輸入要發送的數據:")

# 4. 發送數據到指定的電腦上的指定程序中
udp_socket.sendto(send_data.encode('utf-8'), dest_addr)

# 5. 關閉套接字
udp_socket.close()

在windows中運行“網絡調試助手”:

網絡調試助手接收數據

<4> 接收數據

import socket

# 1. 創建udp套接字
udp_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

# 2. 準備接收方的地址
dest_addr = ('192.168.236.129', 8080)

# 3. 從鍵盤獲取數據
send_data = input("請輸入要發送的數據:")

# 4. 發送數據到指定的電腦上
udp_socket.sendto(send_data.encode('utf-8'), dest_addr)

# 5. 等待接收對方發送的數據
recv_data = udp_socket.recvfrom(1024)  # 1024表示本次接收的最大字節數

# 6. 顯示對方發送的數據
# 接收到的數據recv_data是一個元組
# 第1個元素是對方發送的數據
# 第2個元素是對方的ip和端口
print(recv_data[0].decode('gbk'))
print(recv_data[1])

# 7. 關閉套接字
udp_socket.close()

網絡調試助手截圖:

網絡調試助手接收數據

7 數據解碼和編碼

str->bytes:encode編碼
bytes->str:decode解碼

字符串通過編碼成爲字節碼,字節碼通過解碼成爲字符串。

>>> text = '我是文本'
>>> text
'我是文本'
>>> print(text)
我是文本
>>> bytesText = text.encode()
>>> bytesText
b'\xe6\x88\x91\xe6\x98\xaf\xe6\x96\x87\xe6\x9c\xac'
>>> print(bytesText)
b'\xe6\x88\x91\xe6\x98\xaf\xe6\x96\x87\xe6\x9c\xac'
>>> type(text)
<class 'str'>
>>> type(bytesText)
<class 'bytes'>
>>> textDecode = bytesText.decode()
>>> textDecode
'我是文本'
>>> print(textDecode)
我是文本

其中decode()與encode()方法可以接受參數,其聲明分別爲:

bytes.decode(encoding="utf-8", errors="strict")
str.encode(encoding="utf-8", errors="strict")

其中的encoding是指在解碼編碼過程中使用的編碼格式,errors是指錯誤的處理方案。

注意:

  • strict:表示嚴格按照指定編解碼方式進行編碼和解碼,如果編解碼不成功則拋出異常
  • ignore:表示忽略編解碼不成功的字符,如果編解碼不成功程序不會拋出異常
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章