python Socket无限发送接收数据

一、关于Socket

1.Socket简介

Socket是指套接字,是对网络中不同主机上的应用进程之间进行双向通信的端点的一种抽象。一个套接字就是网络上进程通信的一端,提供了应用层进程利用网络协议交换数据的机制。

2.Socket的主要类型

Socket主要有三种类型:流套接字、数据报套接字、原始套接字。

流套接字(SOCK_STREAM):采用了TCP协议,用于提供面向连接、可靠的数据传输服务。

数据报套接字(SOCK_DGRAM):采用了UDP协议,提供一种无连接的服务。该服务并不能保证数据传输的可靠性,数据有可能在传输过程中丢失或出现数据重复,且无法保证顺序地接收到数据。

原始套接字(SOCK_RAW):与上面两种套接字的区别在于原始套接字可以读写内核没有处理的IP数据包,而流套接字只能读取TCP协议的数据,数据报套接字只能读取UDP协议的数据。

本文中讲的是采用TCP协议,即流套接字。

二、Python的socket模块

Python中进行网络编程的主要是使用socket模块,当然还有高级一点的网络服务模块SocketServer等内容。本文中主要使用的是socket模块。

socket模块中首先需要使用socket()方法创建套接字对象,代码示例如下:

python 复制代码
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

其中,第一个参数是代表套接字家族,一般有socket.AF_UNIX、socket.AF_INET、socket.AF_INET6可以选择。AF_UNIX是本机的通信,AF_INET和AF_INET6分别是IPv4和IPv6。

第二个参数是套接字类型,有socket.SOCK_STREAM、socket.SOCK_DGRAM、socket.SOCK_RAW,分别代表套接字的三种类型。

三、Socket服务端和客户端相关函数

1.服务端使用的函数

函数 描述
s.bind() 绑定地址(host,port)到套接字, 在 AF_INET下,以元组(host,port)的形式表示地址
s.listen() 开始 TCP 监听。参数backlog是指操作系统可以挂起的最大连接数量。该值至少为 1,一般设置为5
s.accept() 被动接受TCP客户端连接,阻塞式等待连接的到来

2.客户端使用的函数

函数 描述
s.connect() TCP服务器连接,参数address的格式为元组(hostname,port),如果连接出错,返回socket.error错误。
s.connect_ex() connect()函数的扩展版本,出错时返回出错码,而不是抛出异常

3.服务端和客户端都可以使用的函数

函数 描述
s.recv() 接收 TCP 数据,数据以字符串形式返回,bufsize 指定要接收的最大数据量
s.send() 发送 TCP 数据,将参数string 中的数据发送到连接的套接字
s.sendall() 完整发送 TCP 数据。将参数 string 中的数据发送到连接的套接字,但在返回之前会尝试发送所有数据。成功返回 None,失败则抛出异常。
s.close() 关闭套接字
s.getpeername() 返回连接套接字的远程地址。返回值通常是元组(ipaddr,port)
s.getsockname() 返回套接字自己的地址。通常是一个元组(ipaddr,port)
s.setsockopt() 设置给定套接字选项的值
s.getsockopt() 返回套接字选项的值
s.settimeout() 设置套接字操作的超时期,参数timeout是一个浮点数,单位是秒。值为None表示没有超时期
s.gettimeout() 返回当前超时期的值,单位是秒,如果没有设置超时期,则返回None
s.setblocking() 如果参数flag为0,则将套接字设为非阻塞模式,否则将套接字设为阻塞模式(默认值)。非阻塞模式下,如果调用recv()没有发现任何数据,或send()调用无法立即发送数据,那么将引起socket.error异常

四、服务器端代码

python 复制代码
import socket

def socket_server():
    server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    ip = ''   # ip可以是127.0.0.1,也可以为空
    port = 0000   # 端口号
    server_socket.bind((ip, port))
    server_socket.listen(5)
    logger.info('等待连接')
    while True:
        try:
            client_socket, address = server_socket.accept()
            logger.info(address[0] + '已连接')
            while True:
                data = client_socket.recv(1024)   # 接受客户端发来的数据
                if not data:
                    logger.info(address[0] + '断开连接')
                    break
                client_socket.send(data.upper())
                """
                可以使用else与上面的if形成搭配
                自己的任意想要实现的功能
				"""
        except ConnectionResetError:
            logger.error(address[0] + '异常断开连接')
            continue
        except KeyboardInterrupt:
            logger.info('服务器关闭')
            break
    server_socket.close()

if __name__ == '__main__':
    socket_server()

五、客户端代码

python 复制代码
import socket

def socket_client():
    client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    ip = ''   # ip可以为127.0.0.1,也可以为服务器的IP,例:10.0.0.xxx
    port = 0000   # 必须与服务器端口号一致
    client_socket.connect((ip, port))

    while True:
        msg = input('>>').strip()
        if not msg:
            continue
        client_socket.send(msg.encode('utf-8'))   # 客户端发送数据
        data = client_socket.recv(1024)   # 接收服务端返回的数据
        print(data.decode("utf-8"))
        # break   无break可以循环发送

    client_socket.close()

if __name__ == '__main__':
    socket_client()

注:客户端和服务端再接收发送数据时,都需要注意数据格式,即decode()和encode()。

相关推荐
全栈软件开发几秒前
PHP域名授权系统网站源码_授权管理工单系统_精美UI_附教程
开发语言·ui·php·php域名授权·授权系统网站源码
誰能久伴不乏5 分钟前
Qt 动态属性(Dynamic Property)详解
开发语言·qt
枫叶丹41 小时前
【Qt开发】常用控件(四)
开发语言·qt
草莓熊Lotso1 小时前
《吃透 C++ 类和对象(中):const 成员函数与取地址运算符重载解析》
c语言·开发语言·c++·笔记·其他
跟橙姐学代码1 小时前
学Python像学做人:从基础语法到人生哲理的成长之路
前端·python
weixin_307779131 小时前
VS Code配置MinGW64编译Ipopt库
开发语言·c++·vscode·算法
Tadas-Gao1 小时前
Java设计模式全景解析:从演进历程到创新实践
java·开发语言·微服务·设计模式·云原生·架构·系统架构
Keying,,,,1 小时前
力扣hot100 | 矩阵 | 73. 矩阵置零、54. 螺旋矩阵、48. 旋转图像、240. 搜索二维矩阵 II
python·算法·leetcode·矩阵
桃源学社(接毕设)1 小时前
基于人工智能和物联网融合跌倒监控系统(LW+源码+讲解+部署)
人工智能·python·单片机·yolov8
yunhuibin2 小时前
pycharm2025导入anaconda创建的各个AI环境
人工智能·python