Python的网络编程socket模块
(1)利用socket进行简单的链接
Python里面的socket支持UDP、TCP、以及进程间的通信,socket可以把我们想要发送的东西封装起来,发送过去,然后反解成原来的样子,事实上网路通信可以理解成都是建立在socket之上,下面的代码是演示利用socket进行简单的链接
#要成一次通信,至少要有两个人,也就是一个服务端,一个客户端 #服务端
'''必须先开启着,等待客户端来进行链接请求,
所以自己要先有个地址,也就是IP,也要现有自己的端口,没有端口进不去''' import socket
sk= socket.socket()#创建对象 sk.bind(('127.0.0.1',9999,))#绑定IP和端口,以一个元组的方式传进去
sk.listen(5)#在前面链接已经建立的情况下,后面最多让五个人等待
while True:#让服务器端处于可以永远处于接受客户端请求的状态 conn,address=sk.accept()
print(conn,address)
'''
监听端口,等待以及接受客户端的请求,有可能会阻塞,主要功能是建立链接,以及接受客户端信息
conn相当于双方建立的这个链接,之后互相的通信要依靠这个链接;
address指的的对方的IP和端口
'''
下面是客户端代码
#客户端
import socket
obj =socket.socket()
'''相对于客户端,制定要链接谁就好了
''' obj.connect(('127.0.0.1',9999,))#链接服务端
obj.close()#链接之后关闭
我们先让服务器端启动,然后再启动客户端,结果如图所示

成功打印出了每次的链接,以及客户端的IP以及端口号
(2)基于socket实现简单的传送消息
#服务器端
import socket
sk= socket.socket() sk.bind(('127.0.0.1',9999,))#绑定IP和端口,以一个元组的方式传进去
sk.listen(5)#在前面链接已经建立的情况下,后面最多让五个人等待
while True:#让服务器端处于可以永远处于接受客户端请求的状态 conn,address=sk.accept()#基于conn这个链接发送东西
conn.sendall(bytes('终有一天你会成为Python爬虫工程师的',encoding='utf-8'))#Python3要用bytes类型,发送字节
'''建立一次链接,服务器就发送这个字段'''
print(conn,address)
然后用是客户端代码
#客户端
import socket
obj =socket.socket()
'''相对于客户端,制定要链接谁就好了
''' obj.connect(('127.0.0.1',9999,))#链接服务端
'''
客户端去链接服务端,如果服务器端没有返回消息给客户端,则客户端会一直
在recv状态,一直等待服务器的消息
'''
result1= obj.recv(2014)#表示最多接收1024个字节,超过了下次接收、
result2= str(result1,encoding='utf-8')
print(result2)
obj.close()#链接之后关闭
当启动一次客户端建立一次链接,就会收到消息,结果如图

(3)基于socket实现聊天机器人
#服务器端
import socket
sk= socket.socket() sk.bind(('127.0.0.1',9999,))#绑定IP和端口,以一个元组的方式传进去
sk.listen(5)#在前面链接已经建立的情况下,后面最多让五个人等待
while True:#让服务器端处于可以永远处于接受客户端请求的状态 conn,address=sk.accept()#基于conn这个链接发送东西
conn.sendall(bytes('你好,链接已经建立',encoding='utf-8'))#Python3要用bytes类型,发送字节
# '''建立一次链接,服务器就先发送这个字段'''
while True:#让通信状态不中断
ret_bytes = conn.recv(1024)
ret_str = str(ret_bytes,encoding='utf-8')
if ret_str =='q':#如果收到q,则终止链接
break
conn.sendall(bytes(ret_str+' 已收到该信息',encoding='utf-8'))
#print(conn,address)
下面是客户端代码
#客户端
import socket
obj =socket.socket()
'''相对于客户端,制定要链接谁就好了
''' obj.connect(('127.0.0.1',9999,))#链接服务端
'''
客户端去链接服务端,如果服务器端没有返回消息给客户端,则客户端会一直
在recv状态,一直等待服务器的消息
''' result1= obj.recv(2014)#表示最多接收1024个字节,超过了下次接收、
result2= str(result1,encoding='utf-8')
print(result2)
while True:
data = input('请输入你要发送的内容:')
if data == 'q':
obj.sendall(bytes(data, encoding='utf-8'))
print('链接断开')
break
else:
obj.sendall(bytes(data,encoding='utf-8'))
rec_byte = obj.recv(1024)#发了之后,接收信息
rec_str = str(rec_byte,encoding='utf-8')
print(rec_str) obj.close()#链接之后关闭
结果如图所示

(4)利用socket传送图片文件
#服务器端
import socket
sk= socket.socket() sk.bind(('127.0.0.1',9999,))#绑定IP和端口,以一个元组的方式传进去
sk.listen(5)#在前面链接已经建立的情况下,后面最多让五个人等待
while True:#
conn,address= sk.accept()
conn.sendall(bytes('链接已建立,可以发送数据了',encoding='utf-8'))
file_size = str(conn.recv(1024),encoding='utf-8')#接收文件大小
print('接收的文件字节数:'+file_size)
total_size = int(file_size)
has_recv = 0#默认已接收了0个字节
f = open('new1.png','wb')
#先接收文件大小,再开始接收文件
while True:
if total_size ==has_recv:#如果已接收的文件大小与客户端发送的一样大,则表示已经接收完毕
break data = conn.recv(1024) f.write(data)
has_recv +=len(data)
print('文件接收成功')
f.close()
下面是客户端
#客户端
import os
import socket
obj =socket.socket() obj.connect(('127.0.0.1',9999,))#链接服务端
'''
客户端去链接服务端,如果服务器端没有返回消息给客户端,则客户端会一直
在recv状态,一直等待服务器的消息
# '''
#obj.sendall(bytes('你好',encoding='utf-8'))
ret_bytes = obj.recv(1024)
ret_str = str(ret_bytes,encoding='utf-8')
print(ret_str) #发送文件大小
size=os.stat('f.jpg').st_size#获取文件大小
obj.sendall(bytes(str(size),encoding='utf-8'),)#文件大小的int型,要先转化为字符串
with open('f.jpg','rb')as f:
for line in f:
obj.sendall(line)
obj.close()
结果如图
(5)socket粘包问题
发送文件需要依赖双方的缓冲区,就是我们先把文件写到缓冲区,然后再发送过去,
但是我们一般不知道什么时候发过去,这容易造成粘包问题。例如上面的例子,客
户端先发送文件大小,然后读文件写进缓冲区,假如文件读取特别快,第一次发送
过去的可能既有文件大小又有文件内容,造成错误,这叫粘包,简而言之就是收到
的信息比原本应收的多。 那么怎么解决粘包问题呢,通过发送以及接收确认包,还是以上面的例子说明,客户
在发送文件大小之后不要马上发送文件,先recv接收一下,等待服务器发送已收到文
件大小的确认包之后,再读取文件、发送文件,这样文件的发送和之前数据的发送就
完全独立开
来了。
#服务器端
import socket
sk= socket.socket() sk.bind(('127.0.0.1',9999,))#绑定IP和端口,以一个元组的方式传进去
sk.listen(5)#在前面链接已经建立的情况下,后面最多让五个人等待
while True:#
conn,address= sk.accept()
conn.sendall(bytes('链接已建立,可以发送数据了',encoding='utf-8')) file_size = str(conn.recv(1024),encoding='utf-8')#接收文件大小
print('接收的文件字节数:'+file_size)
total_size = int(file_size)
has_recv = 0#默认已接收了0个字节
conn.sendall(bytes('文件大小已收到,可以开始发送数据了',encoding='utf-8'))#解决粘包问题,已经收到了文件大小,后面就可以单独发文件了
f = open('new1.png','wb')
#先接收文件大小,再开始接收文件 while True:
if total_size ==has_recv:#如果已接收的文件大小与客户端发送的一样大,则表示已经接收完毕
break data = conn.recv(1024) f.write(data)
has_recv +=len(data)
print('文件接收成功')
f.close()
下面是客户端
#客户端
import os
import socket
obj =socket.socket() obj.connect(('127.0.0.1',9999,))#链接服务端
'''
客户端去链接服务端,如果服务器端没有返回消息给客户端,则客户端会一直
在recv状态,一直等待服务器的消息
# '''
#obj.sendall(bytes('你好',encoding='utf-8'))
ret_bytes = obj.recv(1024)
ret_str = str(ret_bytes,encoding='utf-8')
print(ret_str) #发送文件大小
size=os.stat('f.jpg').st_size#获取文件大小
obj.sendall(bytes(str(size),encoding='utf-8'),)#文件大小的int型,要先转化为字符串
ack_packet=obj.recv(1024)
print(str(ack_packet,encoding='utf-8'))
with open('f.jpg','rb')as f:
for line in f:
obj.sendall(line)
obj.close()
Python的网络编程socket模块的更多相关文章
- 铁乐学Python_Day33_网络编程Socket模块1
铁乐学Python_Day33_网络编程Socket模块1 部份内容摘自授课老师的博客http://www.cnblogs.com/Eva-J/ 理解socket Socket是应用层与TCP/IP协 ...
- python 网络编程--socket模块/struct模块
socket模块: 客户端:CS架构, client -> server 浏览器:BS架构, browser -> server 网络通信本质:传输字节 doc命令查看ip地址:ipc ...
- Python之网络编程Socket
Python 提供了两个级别访问的网络服务.: 低级别的网络服务支持基本的 Socket,它提供了标准的 BSD Sockets API,可以访问底层操作系统Socket接口的全部方法. 高级别的网络 ...
- 网络编程---socket模块
内容中代码都是先写 server端, 再写 client端 1 TCP和UDP对比 TCP(Transmission Control Protocol)可靠的.面向连接的协议(eg:打电话).传输效 ...
- Python的网络编程 Socket编程
Socket是进程间通信的一种方式,与其他进程间通信的一个主要不同是:能实现不同主机间的进程间通信,网络上各种各样的服务大多都是基于Socket来完成通信的,要解决网络上两台主机间的通信问题,首先要唯 ...
- Python之网络编程 Socket编程
本节内容: Socket语法及相关 SocketServer实现多并发 Socket语法及相关 socket概念 socket本质上就是在2台网络互通的电脑之间,架设一个通道,两台电脑通过这个通道来实 ...
- 网络编程socket模块subprocess模块 粘包的解决
什么是socket? tcp 可靠地面向连接协议 udp 不可靠的,无连接的服务,传送效率高
- python网络编程-socket套接字通信循环-粘包问题-struct模块-02
前置知识 不同计算机程序之间数据的传输 应用程序中的数据都是从程序所在计算机内存中读取的. 内存中的数据是从硬盘读取或者网络传输过来的 不同计算机程序数据传输需要经过七层协议物理连接介质才能到达目标程 ...
- python网络编程socket /socketserver
提起网络编程,不同于web编程,它主要是C/S架构,也就是服务器.客户端结构的.对于初学者而言,最需要理解的不是网络的概念,而是python对于网络编程都提供了些什么模块和功能.不同于计算机发展的初级 ...
随机推荐
- windows环境下Nginx部署及Https设置
一.Nginx安装部署及常用命令. 1.1.其实Nginx是免安装的.直接在官网下载zip包,解压即可,下载地址:http://nginx.org/en/download.html,因为我这边的开发服 ...
- YII2 定义页面提示
控制器里面这样写: 单条消息: 键值是规定好的,不要去自定义哦! \Yii::$app->getSession()->setFlash('error', 'This is the mess ...
- 使用Window Media Player网页播放器
近段时间在做一个IETM的项目,项目需要使用WebBrower对包含avi的xml进行显示,可avi的显示总是有问题,网上找到这段在html中播放avi的代码,在Win10上表现不错,明天上班用Win ...
- [VC]C++ operator 两种用法
C++中的operator,有两种用法,一种是operator overloading(操作符重载),一种是operator casting(操作隐式转换).下面分别进行介绍: 1.operato ...
- hdu-1198 Farm Irrigation---并查集+模拟(附测试数据)
题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=1198 题目大意: 有如上图11种土地块,块中的绿色线条为土地块中修好的水渠,现在一片土地由上述的各种 ...
- es6展开运算符
数组的展开合并 现在有两个数组[1, 2, 3, 4]和[5, 6, 7],想要将两个函数拼接成一个新的函数. //es5的写法 let arr1 = [1, 2, 3, 4]; let arr2 = ...
- 3.Cisco Packet Tracer中关于交换机端口安全的设置
本次实验将在这幅拓扑图的基础上完成 我们会对pc0在交换机上进行mac地址绑定,pc1访问时则交换机断开端口 1.为pc机配置ip地址 pc0:192.168.1.1 pc1:192.168.1.2 ...
- Laravel 命令行常用命令
一.简介 1.Artisan 是 Laravel 自带的命令行接口名称,它为我们在开发过程中提供了很多有用的命令.想要查看所有可用的Artisan命令,可使用list命令: php artisan l ...
- 简单聊聊四层/七层模型到HTTP
本文内容借鉴这篇博客:https://blog.csdn.net/agzhchren/article/details/79173491 但是这篇博客也是该博主转载的,文章具体出处我没有找到,如果有人知 ...
- 笔记-HTTP代理
笔记-HTTP代理 1. 基本原理 所谓代理,一个重要的目的是身份伪装,让被访问端无法正辨识访问者的身份. 那么下一个问题是服务器从哪些信息上来识别访问端的身份. 以php http服务器为 ...