Python for Infomatics 第12章 网络编程二(译)
注:文章原文为Dr. Charles Severance 的 《Python for Informatics》。文中代码用3.4版改写,并在本机测试通过。
12.3 用HTTP协议获取一张图片
在上一节的例子中,我们获取的是一个有换行符的文本文件,并简单的把它显示在屏幕上。同样我们可以用一个小程序通过HTTP协议获取图片。下面这个程序运行时,不是直接在屏幕上显示数据,而是剔除头信息,然后将收到的数据合并保存为一个图片文件。具体代码如下:
import socket
import time mysock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
mysock.connect(('www.py4inf.com', 80))
mysock.send(b'GET http://www.py4inf.com/cover.jpg HTTP/1.0\n\n') count = 0
picture = b""
while True:
data = mysock.recv(5120)
if ( len(data) < 1 ) :
break
# time.sleep(0.25)
count = count + len(data)
print(len(data), count)
picture = picture + data
mysock.close() # Look for end of the header (2 CRLF)
pos = picture.find(b"\r\n\r\n")
print('Header length', pos)
print(picture[:pos].decode("utf-8")) # Skip past the header and save the picture
picture = picture[pos+4:]
fhand = open("stuff.jpg", "wb")
fhand.write(picture)
fhand.close()
运行程序,输出如下:
5120 5120
5120 10240
5120 15360
5120 20480
5120 25600
5120 30720
960 31680
5120 36800
5120 41920
2384 44304
3752 48056
5120 53176
5120 58296
5120 63416
5120 68536
1767 70303
Header length 242
HTTP/1.1 200 OK
Date: Sat, 23 Apr 2016 06:51:38 GMT
Server: Apache
Last-Modified: Fri, 04 Dec 2015 19:05:04 GMT
ETag: "b294001f-111a9-526172f5b7cc9"
Accept-Ranges: bytes
Content-Length: 70057
Connection: close
Content-Type: image/jpeg
正如你看到的,它的内容类型头信息表明这个文档的主体是一张图片。一旦程序运行结束,你就可以用图片查看器打开stuff.jpg文件,你会发现这是本书的封面。
从程序运行过程中,可以看到我们并不是每次都接收到5120个字符。在我们调用recv()方法的那个时刻,我们收到的字符数和网页服务器发给我们的一样多。在这个例子中有960,2384到最多5120个字符。因为你的网速会有所不同,所以你的输出也会不同。同时要注意的是我们收到的最后一批码流是1767个,下一次调用recv()我们将收到零长度的字符串,这告诉我们服务器已调用close()关闭了它那端的套接字,并且不会再有数据发送过来。
我们可以取消time.sleep()的注释,减缓我们连续调用recv()的时间间隔。通过这种方式,我们在每次调用前等待1/4秒,从而让服务器赶上我们在调用recv()之前发送更多的数据。添加延时后程序的运行结果如下:
5120 5120
5120 10240
....
5120 66560
3743 70303
Header length 242
HTTP/1.1 200 OK
Date: Sat, 23 Apr 2016 07:38:55 GMT
Server: Apache
Last-Modified: Fri, 04 Dec 2015 19:05:04 GMT
ETag: "b294001f-111a9-526172f5b7cc9"
Accept-Ranges: bytes
Content-Length: 70057
Connection: close
Content-Type: image/jpeg
现在除了最后一次调用少于5120外,其它我们每次都接收到5120个(注:可能是网速的原因,译者的第一次接收也是5120个,而原文中第一次也小于5120)。这是服务器的发送和我们的接收共同约定的缓冲区容量。当我们采用延时接收时,在某些时刻服务器的发送可能填满这个缓冲区,从而不得不停止发送,只到我们的程序清空缓冲区。这个在发送和接收程序间的停顿被叫做流量控制。
12.4 用urllib获取网页
虽然我们可以用socket库在HTTP协议上人工发送和接收数据,但是在Python中用urllib库来完成这项常见任务来得更加简单。
用urllib,你可以把网页看作是一个文件,你只要简单地指出你要哪个网页,剩下的就由urllib来处理了。
与用socket读取romeo.txt具备相同功能的urllib代码如下:
import urllib.request
fhand = urllib.request.urlopen('http://www.py4inf.com/code/romeo.txt')
for line in fhand:
print(line.strip().decode('utf-8'))
一旦这个网页被urllib.request.urlopen打开,我们就可以把它看作一个文件,并且循环读取。
当运行这个程序时,我们只能看到文件的内容。虽然文件头仍然被发送,但是urllib代码消除了文件头,只返回以下内容:
But soft what light through yonder window breaks
It is the east and Juliet is the sun
Arise fair sun and kill the envious moon
Who is already sick and pale with grief
下个例子中,我们在获取romeo.txt之后,计算文件中每个词出现的频率:
import urllib.request
counts = dict()
fhand = urllib.request.urlopen('http://www.py4inf.com/code/romeo.txt')
for line in fhand:
words = line.decode('utf-8').split()
for word in words:
counts[word] = counts.get(word,0) + 1
print (counts)
代码的输出结果如下:
{'is': 3, 'kill': 1, 'light': 1, 'sun': 2, 'Arise': 1, 'moon': 1, 'It': 1, 'yonder': 1, 'the': 3, 'But': 1, 'fair': 1, 'and': 3, 'east': 1, 'soft': 1, 'Juliet': 1, 'grief': 1, 'already': 1, 'breaks': 1, 'envious': 1, 'sick': 1, 'pale': 1, 'what': 1, 'through': 1, 'Who': 1, 'with': 1, 'window': 1}
再次说明,一旦我们打开了这个网页,我们就可以像本地文档一样读取它。
Python for Infomatics 第12章 网络编程二(译)的更多相关文章
- Python for Infomatics 第12章 网络编程一(译)
注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 本书中的许多例子关注的是读取文件 ...
- Python for Infomatics 第12章 网络编程六(译)
注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 12.9 词汇表 Beautif ...
- Python for Infomatics 第12章 网络编程五(译)
注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 12.8 用urllib读取二进 ...
- Python for Infomatics 第12章 网络编程四(译)
注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 12.7 用BeautifulS ...
- Python for Infomatics 第12章 网络编程三(译)
注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 12.5 HTML分析和网页抓取 ...
- python之路(12)网络编程
前言 基于网络通信(AF_INET)的socket(套接字)实现了TCP/UDP协议 目录 基于TCP协议的socket 基于UDP协议的socket TCP协议下粘包现象及处理 使用socketse ...
- Python for Infomatics 第13章 网页服务二(译)
注:文章原文为Dr. Charles Severance 的 <Python for Informatics>.文中代码用3.4版改写,并在本机测试通过. 13.4 JavaScript ...
- CSAPP:第十一章 网络编程
CSAPP:第十一章 网络编程 11.1 客户端服务器模型11.2 全球IP因特网11.3 套接字接口 11.1 客户端服务器模型 每个网络应用都是基于客户端-服务器模型.采用这个模型,一个应用是 ...
- Python学习day34-面向对象和网络编程总结
figure:last-child { margin-bottom: 0.5rem; } #write ol, #write ul { position: relative; } img { max- ...
随机推荐
- Java Web笔记之Servlet(1)
今天在学习Servlet时,使用浏览器显示的网页效果与预期的有差异,仔细查找发现实<!DOCTYPE>声明的问题,截图如下: 代码如下: package secondServlet; im ...
- Migrating an Existing Website from SQL Membership to ASP.NET Identity
Migrating an Existing Website from SQL Membership to ASP.NET Identity public class User : IdentityUs ...
- Excel 锁定特定单元格 不允许更改
1.首先,excel默认所有单元格都是被"锁定"的--当"锁定单元格"按钮被激活时. 因此,第一步,选择所有单元格,设置单元格格式,取消"保护&quo ...
- PHP函数call_user_func和call_user_func_array详解
今天在群里面,有个叫lewis的在问call_user_func_array的用法,因为之前一直没有用过,也不能说什么,于是看一下手册,发现是这么写的: call_user_func_array (P ...
- Linux/CentOS 服务安装/卸载,开机启动chkconfig命令详解|如何让MySQL、Apache开机启动?
chkconfig chkconfig在命令行操作时会经常用到.它可以方便地设置和查询不同运行级上的系统服务.这个可要好好掌握,用熟练之后,就可以轻轻松松的管理好你的启动服务了. 注:谨记chkcon ...
- javascript数据结构-数组
github博客地址 简介 数组是最简单的数据结构,javascript语言也很早就原声支持了数组Array数据类型,和其他语言略微不同的是:js中的数组可以存储不同类型的值,看起来很厉害的样子,但是 ...
- 安卓APP关于切图标
bin res drawable-hdpi drawable-ldpi drawable-mdpi drawable-nodpi drawable-xhdpi drawable-xxhdpi x越大代 ...
- java 深入技术三(List)
List ArrayList List接口 List接口的父接口-Collection List接口的重要子类- ArrayList -LikedList List接口不重要子类-Vector jav ...
- plist文件的读写
参考资料 http://blog.csdn.net/totogo2010/article/details/7634185
- iOS 编码转换
- (NSString *)SaveFileToDocuments:(NSString *)url { // NSString *url = @"http://172.28.250.70/a ...