9.2 Socket编程
远程管理软件和黑客软件大多依赖于Socket来实现特定功能,前几年流行的端口反弹更是把这项技术发挥到了极致。
如前所述,UDP和TCP是网络体系结构的传输层运行的两大重要协议,其中,TCP适用于对效率要求相对低而准确性要求相对高的场合,如文本传输、电子邮件等;而UDP适用于对效率要求相对高,对准确性要求相对低的场合,如视频在线点播、网络语音通话等。在Python中,主要使用socket模块来支持TCP和UDP编程。
9.2.1 UDP编程
在很多年以前普通家庭还没有手机、电话、传呼机的时候,主要靠信件往来联系,发信人提哦啊好收信人地址然后把信件寄出去就可以了,但是没法保证对方一定能收到这封信(例如对方换了地址),也不能保证不同时间的几封信按照发出的顺序到达目的地。UDP的工作过程就类似于邮寄普通信件,它属于无连接协议,在UDP编程时不需要首先建立连接,而是直接向接收方发送信息。UDP也不提供应答和重传机制,无法保证数据一定鞥能够到达目的地。UDP最大的优点是效率高,其首部中只包含双发地址于校验等很少的字段,额外开销很小。UDP编程经常用到的socket模块方法如下。
(1)socket([family[,type[,proto]]] :创建一个Socket对象,其中family为socket.AF_INET表示IPv4,AF_INET6表示IPv6;type为SOCK_STREAM表示使用TCP,SOCK_DGRAM表示使用UDP。
(2)sendto(string,address):把string指定的内容发送给address指定的地址,其中address是一个包含接收方主机IP地址的应用进程端号的元组,格式为(IP地址,端口号)。
(3)recvfrom(bufsize[,flags]):接收数据。
下面通过一个示例来简单了解一个如何使用UDP进行网络通信。
发送端发送一个字符串,假设接收端在本机5000端口进行监听,并显示接受的内容,如果收到字符串'bye'(忽略大小写)则结束监听。
接收端代码:
import socket #使用IPv4协议,使用UDP传输数据
s = socket.socket(socket.AF_INET,socket.SOCK_DGRAM) #绑定端口和端口好,空字符串表示本机任何可用IP地址
s.bind('',5000) while True:
data,addr = s.recvfrom(1024) #显示接收到的内容
print('received message:{0} from PORT{1} on {2}'.format(data.decode(),addr[1],addr[0])) if data.decode().lower() == 'bye':
break s.close()
发送端代码:
import socket
import sys s = socket.socket(socket.AF_INET,socket.SOCK_DGRAM) #假设192.168.1.103是接收端机器的IP地址
s.sendto(sys.argv[1].encode(),('192.168.1.103',5000)) s.close()
将上面的代码分别保存为receiver.py和sender.py,然后首先启动一个命令提示符环境并运行接收端程序,这时接收端程序处于阻塞状态,接下来再启动一个新的命令体书法环境并运行发送端程序,此时会看到接收端程序继续运行并显示接收到的内容以及发送端程序所在计算机IP地址和占用的端口号。当发送端发送字符串'bye'后,接收单程序结束,此后再次运行发送端程序时接收端没有任何反应,但发送端程序也并不报错。这就是UDP的特点,即“尽最大努力传输”,并不能保证非常好的服务质量。
可以使用下面的Python代码来获取本机的IP地址和网卡的物理地址。
ip = socket.gethostbyname(socket.gethostname()) #本机IP地址
node = uuid.getnode()
print('node:',node) macHex = uuid.UUID(int=node).hex[-12:]
mac = []
print(macHex)
for i in range(len(macHex))[::2]:
mac.append(macHex[i:i+2]) mac1 = ':'.join(mac) #网卡的物理地址 print('IP:',ip)
print('MAC:',mac1)
拓展知识:发送数据时,如果目标IP地址中最后一组数字是255,表示广播地址,也就是说局域网内的所有主机都会受到信息。
9.2.2 TCP 编程
TCP一般用于要求可靠数据传输的场合。编写TCP程序是需要用到的socket模块方法主要如下。
(1)connect(address):连接远程计算机。
(2)send(bytes[,flags]):发送数据。
(3)recv(bufsize[,flags]):接收数据。
(4)bind(address):绑定地址。
(5)listen(backlog):开始监听,等待客户端连接。
(6)accept():响应客户端的请求,接收一个连接。
下面通过一个示例来演示如何使用TCP进行通信。会聊天的小机器人。
使用TCP进行铜线需要首先在客户端和服务端之间建立连接,并且要在通信结束后关闭连接以释放资源。TCP能够提供比UDP更好的服务质量,通信可靠性有本质上的提高。下面的代码简单模拟了机器人聊天软件原理,服务端提前建立好字典,可以根据收到的内容自动回复。
服务端代码:
import socket
words = {'how are you?':'Fine,thank you','how old are you?':'','what is your name?':'Dong FuGuo',"what's your name?":'DongFuGuo',
'where do you work?':'SDIBT','bye':'BYE'}
HOST = ''
PORT=50007
s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
#绑定socket
s.bind((HOST,PORT))
#开始监听一个客户端连接
s.listen(1)
print('Listening at port:',PORT)
conn,addr = s.accept()
print('Connected by',addr)
while True:
data = conn.recv(1024)
data = data.decode()
if not data:
break
print('Received message:',data)
conn.sendall(words.get(data,'Nothing').encode())
conn.close()
s.close()
客户端代码:
import socket, sys # 服务端主机的IP地址和端口好
HOST = '192.168.1.101'
PORT = 50007
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
try:
# 连接服务器
s.connect((HOST, PORT))
except Exception as e:
print('Server not found or not open')
sys.exit() while True:
c = input('Input the content you want to send:')
# 发送数据
s.sendall(c.encode()) # 从服务器端接收数据
data = s.recv(1024)
print('Received:', data)
if c.lower() == 'bye':
break # 关闭连接
s.close()
扩展知识:Python标准库socket处理支持UDP和TCP编程之外,还提供了用来获取本地主机名的gethostname()、根据主机名获取IP地址的gethostbyname()、根据IP地址获取主机名的gethostbyaddr()、根据端口号获取对应服务名称的getservbyport()、根据服务名称获取对应端口号的getservbyname()等方法。
9.2 Socket编程的更多相关文章
- Linux下的C Socket编程 -- server端的继续研究
Linux下的C Socket编程(四) 延长server的生命周期 在前面的一个个例子中,server在处理完一个连接后便会立即结束掉自己,然而这种server并不科学啊,server应该是能够一直 ...
- java socket编程(li)
一.网络编程中两个主要的问题 一个是如何准确的定位网络上一台或多台主机,另一个就是找到主机后如何可靠高效的进行数据传输.在TCP/IP协议中IP层主要负责网络主机的定位,数据传输的路由,由IP地址可以 ...
- Python Socket 编程——聊天室示例程序
上一篇 我们学习了简单的 Python TCP Socket 编程,通过分别写服务端和客户端的代码了解基本的 Python Socket 编程模型.本文再通过一个例子来加强一下对 Socket 编程的 ...
- Linux下的C Socket编程 -- server端的简单示例
Linux下的C Socket编程(三) server端的简单示例 经过前面的client端的学习,我们已经知道了如何创建socket,所以接下来就是去绑定他到具体的一个端口上面去. 绑定socket ...
- Linux下的C Socket编程 -- 获取对方IP地址
Linux下的C Socket编程(二) 获取域名对应的IP地址 经过上面的讨论,如果我们想要连接到远程的服务器,我们需要知道对方的IP地址,系统函数gethostbyname便能够实现这个目的.它能 ...
- Linux下的C Socket编程 -- 简介与client端的处理
Linux下的C Socket编程(一) 介绍 Socket是进程间通信的方式之一,是进程间的通信.这里说的进程并不一定是在同一台机器上也有可能是通过网络连接的不同机器上.只要他们之间建立起了sock ...
- python网络编程-socket编程
一.服务端和客户端 BS架构 (腾讯通软件:server+client) CS架构 (web网站) C/S架构与socket的关系: 我们学习socket就是为了完成C/S架构的开发 二.OSI七层 ...
- Socket编程实践(2) Socket API 与 简单例程
在本篇文章中,先介绍一下Socket编程的一些API,然后利用这些API实现一个客户端-服务器模型的一个简单通信例程.该例子中,服务器接收到客户端的信息后,将信息重新发送给客户端. socket()函 ...
- Socket编程实践(1) 基本概念
1. 什么是socket socket可以看成是用户进程与内核网络协议栈的编程接口.TCP/IP协议的底层部分已经被内核实现了,而应用层是用户需要实现的,这部分程序工作在用户空间.用户空间的程序需要通 ...
- [转]C语言SOCKET编程指南
1.介绍 Socket编程让你沮丧吗?从man pages中很难得到有用的信息吗?你想跟上时代去编Internet相关的程序,但是为你在调用 connect() 前的bind() 的结构而不知所措?等 ...
随机推荐
- ALSA声卡驱动中的DAPM详解之七:dapm事件机制(dapm event)
前面的六篇文章,我们已经讨论了dapm关于动态电源管理的有关知识,包括widget的创建和初始化,widget之间的连接以及widget的上下电顺序等等.本章我们准备讨论dapm框架中的另一个机制:事 ...
- 超级有用的git reset --hard和git revert命令
很多时候,git新手容易误操作,比如,在levelIISZ-1.4.dev分支下,运行了git pull idc cpp-1.0的结果,这样做麻烦很大,经常导致maven项目格式不正确,这个时候,可以 ...
- YTU 2732:3798-Abs Problem
2732: 3798-Abs Problem 时间限制: 1 Sec 内存限制: 128 MB Special Judge 提交: 167 解决: 60 题目描述 Alice and Bob i ...
- Scikit-learn库中的数据预处理(一)
数据标准化:当单个特征的样本取值相差甚大或明显不遵从高斯正态分布时,标准化表现的效果较差.实际操作中,经常忽略特征数据的分布形状,移除每个特征均值,划分离散特征的标准差,从而等级化,进而实现数据中心化 ...
- spark 操作Hive时遇到的问题
To adjust logging level use sc.setLogLevel(newLevel). For SparkR, use setLogLevel(newLevel).17/10/14 ...
- ural 1009. K-based Numbers(简单dp)
http://acm.timus.ru/problem.aspx?space=1&num=1009 题意:将一个n位数转化为合法的K进制数,有多少种情况.合法的K进制数即不含前导0,且任意两个 ...
- Gym - 101208C 2013 ACM-ICPC World Finals C.Surely You Congest 最大流+最短路
题面 题意:给你n(2w5)个点,m条边(7w5)有k(1e3)辆车停在某些点上的,然后他们都想尽快去1号点,同时出发,同一个点不允许同时经过, 如果多辆车同时到达一个点,他们就会堵塞,这时候只能选择 ...
- akka设计模式系列(Actor模型)
谈到Akka就必须介绍Actor并发模型,而谈到Actor就必须看一篇叫做<A Universal Modular Actor Formalism for Artificial Intellig ...
- zb的生日-------搜索 和 动态规划
简单的贪心算法 : http://love-oriented.com/pack/P01.html 说实话 我是喜欢 动态规划的.......但是省赛迫在眉睫 , 只好先 学 搜索了 , 赶紧 ...
- NS2学习笔记(三)
代理(Agents) 代理是网络层数据包产生和使用的端点,用于实现多层的协议.Agent类部分用OTcl实现,部分用C++实现.C++的代码在~ns/agent.cc和~ns/agent.h中,OTc ...