我是靠谱客的博主 懦弱蚂蚁,最近开发中收集的这篇文章主要介绍树莓派python网络通信_【玩树莓】编程篇(二)Python TCP、UDP 网络编程,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

1. TCP编程

TCP协议是网络通信领域使用最广泛的协议之一。

和其他Linux下的编程方式一样,Python的TCP通信也可以基于Socket方式实现。TCP通信协议通过建立连接和应答来保证通信质量,它将通信设备分为Server和Client,两者的操作方式也有些区别。

1.1. TCP Server和Client

Server基本流程为:创建Socket -> 绑定IP和端口 -> 在绑定的IP和端口上监听连接请求 -> 接受Client发出的连接请求 -> 收发收据 -> 关闭连接。

下面是一个简单的例子,实现了基本的TCP Server功能。

import socket

import time

import sys

HOST_IP = "137.58.230.162"

HOST_PORT = 7654

#创建Socket,SOCK_STREAM表示类型为TCP

print("Starting socket: TCP...")

socket_tcp = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

#绑定IP和端口,并进行监听

#137.58.230.162为本机IP,端口为7654

print("TCP server listen @ %s:%d!" %(HOST_IP, HOST_PORT) )

host_addr = (HOST_IP, HOST_PORT)

socket_tcp.bind(host_addr)

socket_tcp.listen(1)

#接受Client发出的连接请求,返回值包含了Client的IP和端口

socket_con, (client_ip, client_port) = socket_tcp.accept()

print("Connection accepted from %s." %client_ip)

#向Clinet发送数据

socket_con.send("Welcome to RPi TCP server!")

socket_tcp.close()

Client对应的流程要简单的多:创建Socket -> 向服务器发出连接请求 -> 连接建立成 -> 收发收据 -> 关闭连接。

代码如下:

import socket

import time

import sys

SERVER_IP = "137.58.230.162"

SERVER_PORT = 7654

#创建Socket,SOCK_STREAM表示类型为TCP

print("Starting socket: TCP...")

socket_tcp = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

#向服务器发出连接请求,需要指定服务器IP和端口

print("Connecting to server @ %s:%d..." %(SERVER_IP, SERVER_PORT))

server_addr = (SERVER_IP, SERVER_PORT)

socket_tcp.connect(server_addr)

#接收服务器发来的欢迎数据

data = socket_tcp.recv(512)

print("Server: %s" %data)

socket_tcp.close()

在树莓派上运行TCP Server,Client可以同时在树莓派上运行来测试通信,或者在其他网络设备上运行。当然,这种完成通信就直接关闭Socket的方法简单粗暴,实际的应用应当包含更完善的断开连接和异常处理机制。

在树莓派上运行TCP Server

在树莓派上运行TCP Client

在PC上运行TCP Client

1.2. TCP数据传输

下面的代码实现了Server端和Client端的双向数据收发。其基本结构与之前的例子相同,但是多出了错误检测的部分。

Server端的代码中,try…except…部分循环接收Client发来的数据,然后给出回应。程序一旦出现错误,如对方断开连接,就退出程序。

import socket

import time

import sys

HOST_IP = "137.58.230.162"

HOST_PORT = 7654

print("Starting socket: TCP...")

host_addr = (HOST_IP, HOST_PORT)

socket_tcp = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

print("TCP server listen @ %s:%d!" %(HOST_IP, HOST_PORT) )

socket_tcp.bind(host_addr)

socket_tcp.listen(1)

socket_con, (client_ip, client_port) = socket_tcp.accept()

print("Connection accepted from %s." %client_ip)

socket_con.send("Welcome to RPi TCP server!")

print("Receiving package...")

while True:

try:

data = socket_con.recv(512)

if len(data)>0:

print("Received: %s" %data)

socket_con.send("OK!")

time.sleep(1)

continue

except Exception:

socket_tcp.close()

sys.exit(1)

Client端的代码增加了尝试连接部分,如果连接不成功报错,如服务器超时无响应,就等待一段时间再重新发起连接请求。

import socket

import time

import sys

SERVER_IP = "137.58.230.162"

SERVER_PORT = 7654

print("Starting socket: TCP...")

server_addr = (SERVER_IP, SERVER_PORT)

socket_tcp = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

while True:

try:

print("Connecting to server @ %s:%d..." %(SERVER_IP, SERVER_PORT))

socket_tcp.connect(server_addr)

break

except Exception:

print("Can't connect to server, try it latter!")

time.sleep(1)

continue

print("Receiving package...")

while True:

try:

data = socket_tcp.recv(512)

if len(data)>0:

print("Received: %s" %data)

socket_tcp.send("Hello TCP!")

time.sleep(1)

continue

except Exception:

socket_tcp.close()

socket_tcp = None

sys.exit(1)

软件运行效果如图:

Server端,收到Client的数据并回应

Client端,收到Server发来的欢迎信息和回应

2. UDP编程

UDP是TCP之外的另一重要协议,由于没有连接和应答机制,UDP传输并不可靠。通过UDP发出的数据包并不能保证安全抵达目的地。但是像网络语音通话之类对数据完整性要求不太高的应用,就可以采用UDP方式。同时语音通话不适合使用重传,之前说的一句话没听到过了一会儿突然蹦出来了算什么……

2.1. UDP数据传输

下面两段代码分别演示了UDP的数据发送和接收,相比TCP省去了连接部分,代码更加简单。

发送部分:

import socket

import time

DST_IP = "137.58.230.162"

DST_PORT = 8888

#建立Socket,SOCK_DGRAM表示Socket类型为UDP

print("Starting socket: UDP...")

socket_udp = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

#向目的地址和端口,发送数据

print("Sending package to %s:%d..." %(DST_IP, DST_PORT))

dst_addr = (DST_IP, DST_PORT)

while True:

socket_udp.sendto("Hello UDP!", dst_addr)

time.sleep(1)

continue

接收部分:

import socket

import time

HOST_IP = "137.58.230.162"

HOST_PORT = 8888

#建立Socket,SOCK_DGRAM表示Socket类型为UDP

print("Starting socket: UDP...")

socket_udp = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

#绑定本机IP和端口,在此端口上接收数据

print("UDP server bind @ %s:%d!" %(HOST_IP, HOST_PORT) )

host_addr = (HOST_IP, HOST_PORT)

socket_udp.bind(host_addr)

#接收数据,同时显示数据的源地址

print("Receiving package...")

while True:

data, (src_addr, src_port) = socket_udp.recvfrom(512)

if len(data)>0:

print("Received from %s: %s" %(src_addr, data))

time.sleep(1)

continue

UDP数据发送

UDP数据接收

2.2. UDP多线程操作

如果想要在一个程序中同时接收和发送数据就要复杂一些了。这里给出了一个多线程操作的例子:在程序的主线程中接收数据,同时新建一个线程来发送数据,发送线程循环执行send_thread()函数中的内容。这里,147.214.210.229为本机的地址,接收端口为7777。目的地址和端口分别为137.58.230.162和8888。

import socket

import time

import thread

HOST_IP = "147.214.210.229"

HOST_PORT = 7777

host_addr = (HOST_IP, HOST_PORT)

DST_IP = "137.58.230.162"

DST_PORT = 8888

dst_addr = (DST_IP, DST_PORT)

# UDP 数据发送线程

def send_thread():

print("Starting TX socket: UDP...")

socket_udp_tx = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

while True:

socket_udp_tx.sendto("Hello UDP!", dst_addr)

time.sleep(1)

# UDP 数据接收部分

print("Starting TX thread...")

thread.start_new_thread(send_thread, ())

print("Starting RX socket: UDP...")

socket_udp_rx = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

print("UDP server bind @ %s:%d!" %(HOST_IP, HOST_PORT) )

socket_udp_rx.bind(host_addr)

print("Receiving package...")

while True:

data, (src_addr, src_port) = socket_udp_rx.recvfrom(512)

if len(data)>0:

print("Received from %s: %s" %(src_addr, data))

continue

该程序可以运行在两个不同的设备上,只要将本机地址和目的地址对调即可。

运行程序,即可看到两台设备互相发送数据的信息:

树莓派上运行的UDP收发程序

PC上运行的UDP收发程序

最后

以上就是懦弱蚂蚁为你收集整理的树莓派python网络通信_【玩树莓】编程篇(二)Python TCP、UDP 网络编程的全部内容,希望文章能够帮你解决树莓派python网络通信_【玩树莓】编程篇(二)Python TCP、UDP 网络编程所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(49)

评论列表共有 0 条评论

立即
投稿
返回
顶部