- ubuntu12.04环境下使用kvm ioctl接口实现最简单的虚拟机
- Ubuntu 通过无线网络安装Ubuntu Server启动系统后连接无线网络的方法
- 在Ubuntu上搭建网桥的方法
- ubuntu 虚拟机上网方式及相关配置详解
CFSDN坚持开源创造价值,我们致力于搭建一个资源共享平台,让每一个IT人在这里找到属于你的精彩世界.
这篇CFSDN的博客文章浅谈Python爬取网页的编码处理由作者收集整理,如果你对这篇文章有兴趣,记得点赞哟.
背景 。
中秋的时候,一个朋友给我发了一封邮件,说他在爬链家的时候,发现网页返回的代码都是乱码,让我帮他参谋参谋(中秋加班,真是敬业= =!),其实这个问题我很早就遇到过,之前在爬小说的时候稍微看了一下,不过没当回事,其实这个问题就是对编码的理解不到位导致的.
问题 。
很普通的一个爬虫代码,代码是这样的:
1
2
3
4
5
6
7
8
9
10
|
# ecoding=utf-8
import
re
import
requests
import
sys
reload
(sys)
sys.setdefaultencoding(
'utf8'
)
url
=
'http://sz.lianjia.com/ershoufang/rs%E6%8B%9B%E5%95%86%E6%9E%9C%E5%B2%AD/'
res
=
requests.get(url)
print
res.text
|
目的其实很简单,就是爬一下链家的内容,但是这样执行之后,返回的结果,所有涉及到中文的内容,全部会变成乱码,比如这样 。
1
2
3
4
5
6
7
|
<script
type
=
"text/template"
id
=
"newAddHouseTpl"
>
<div
class
=
"newAddHouse"
>
自从您上次æµè§ˆï¼ˆ<
%
=
time
%
>)之åŽï¼Œè¯¥æœç´¢æ¡ä»¶ä¸‹æ–°å¢žåŠ 了<
%
=
count
%
>套房æº
<a href
=
"<%=url%>"
class
=
"LOGNEWERSHOUFANGSHOW"
<
%
=
logText
%
>><
%
=
linkText
%
><
/
a>
<span
class
=
"newHouseRightClose"
>x<
/
span>
<
/
div>
<
/
script>
|
这样的数据拿来可以说毫无作用.
问题分析 。
这里的问题很明显了,就是文字的编码不正确,导致了乱码.
查看网页的编码 。
从爬取的目标网页的头来看,网页是用utf-8来编码的.
1
|
<meta http
-
equiv
=
"Content-Type"
content
=
"text/html; charset=utf-8"
>
|
所以,最终的编码,我们肯定也要用utf-8来处理,也就是说,最终的文本处理,要用utf-8来解码,也就是:decode('utf-8') 。
文本的编码解码 。
Python的编码解码的过程是这样的,源文件 ===》 encode(编码方式) ===》decode(解码方式),在很大的程度上,不推荐使用 。
1
2
3
|
import
sys
reload
(sys)
sys.setdefaultencoding(
'utf8'
)
|
这种方式来硬处理文字编码。不过在某些时候不影响的情况下,偷偷懒也不是什么大问题,不过比较建议的就是获取源文件之后,使用encode和decode的方式来处理文本.
回到问题 。
现在问题最大的是源文件的编码方式,我们正常使用requests的时候,它会自动猜源文件的编码方式,然后转码成Unicode的编码,但是,毕竟是程序,是有可能猜错的,所以如果猜错了,我们就需要手工来指定编码方式。官方文档的描述如下:
When you make a request, Requests makes educated guesses about the encoding of the response based on the HTTP headers. The text encoding guessed by Requests is used when you access r.text. You can find out what encoding Requests is using, and change it, using the r.encoding property. 。
所以我们需要查看requests返回的编码方式到底是什么?
1
2
3
4
5
6
7
8
9
10
11
12
|
# ecoding=utf-8
import
re
import
requests
from
bs4
import
BeautifulSoup
import
sys
reload
(sys)
sys.setdefaultencoding(
'utf8'
)
url
=
'http://sz.lianjia.com/ershoufang/rs%E6%8B%9B%E5%95%86%E6%9E%9C%E5%B2%AD/'
res
=
requests.get(url)
print
res.encoding
|
打印的结果如下:
ISO-8859-1 。
也就是说,源文件使用的是ISO-8859-1来编码。百度一下ISO-8859-1,结果如下:
ISO8859-1,通常叫做Latin-1。Latin-1包括了书写所有西方欧洲语言不可缺少的附加字符.
问题解决 。
发现了这个东东,问题就很好解决了,只要指定一下编码,就能正确的打出中文了。代码如下:
1
2
3
4
5
6
7
8
9
10
11
12
|
# ecoding=utf-8
import
requests
import
sys
reload
(sys)
sys.setdefaultencoding(
'utf8'
)
url
=
'http://sz.lianjia.com/ershoufang/rs%E6%8B%9B%E5%95%86%E6%9E%9C%E5%B2%AD/'
res
=
requests.get(url)
res.encoding
=
(
'utf8'
)
print
res.text
|
打印的结果就很明显,中文都正确的显示出来了.
另一种方式是在源文件上做解码和编码,代码如下:
1
2
3
4
5
6
7
8
9
10
11
12
|
# ecoding=utf-8
import
requests
import
sys
reload
(sys)
sys.setdefaultencoding(
'utf8'
)
url
=
'http://sz.lianjia.com/ershoufang/rs%E6%8B%9B%E5%95%86%E6%9E%9C%E5%B2%AD/'
res
=
requests.get(url)
# res.encoding = ('utf8')
print
res.text.encode(
'ISO-8859-1'
).decode(
'utf-8'
)
|
另:ISO-8859-1也叫做latin1,使用latin1做解码结果也是正常的.
关于字符的编码,很多东西可以说,想了解的朋友可以参考以下大神的资料.
•《The Absolute Minimum Every Software Developer Absolutely, Positively Must Know About Unicode and Character Sets (No Excuses!)》 。
以上这篇浅谈Python爬取网页的编码处理就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持我.
最后此篇关于浅谈Python爬取网页的编码处理的文章就讲到这里了,如果你想了解更多关于浅谈Python爬取网页的编码处理的内容请搜索CFSDN的文章或继续浏览相关文章,希望大家以后支持我的博客! 。
我在字符串中有一个大词。例子白 Wine 额外优惠。 我想在第一行使用“White”,在第二行使用“wine extra offer”。使用下面的代码: string value="White win
我想在无符号中执行一些算术运算,需要取负整数的绝对值,比如 do_some_arithmetic_in_unsigned_mode(int some_signed_value) { unsign
我正在努力使用 data.table 来总结向量函数的结果,这在 ddply 中很容易。 问题 1:使用带有矢量输出的(昂贵的)函数聚合 dt dt[ , as.list(quantile(x)),
我有两个分数列表; 说 A = [ 1/212, 5/212, 3/212, ... ] 和 B = [ 4/143, 7/143, 2/143, ... ] . 如果我们定义 A' = a[0] *
我已经使用 numpy 从 csv 文件中获取数据。 numpy 数组的尺寸为:100*20。我如何取列的平均值(比如 col 3,5,8)并用包含这 3 个 cols 平均值的新列替换它们 如果
在 Rust 中取任意数的 n 次根的最佳方法是什么?例如,num crate 只允许取整数类型的第 n 个主根,即 floor'ed 或 ceil'ed 值......如何最好地接近实际值? 最佳答
看起来这应该很容易,但我很困惑。我已经掌握了使用 dplyr 进行编程的大致技巧0.7,但为此苦苦挣扎:How do Iprogram in dplyr我想要编程的变量是否是一个字符串? 我正在抓取数
在 Rust 中取任意数的 n 次根的最佳方法是什么?例如,num crate 只允许取整数类型的第 n 个主根,即 floor'ed 或 ceil'ed 值......如何最好地接近实际值? 最佳答
我有一个 pandas 数据框,其中有一列名为“coverage”。对于一系列特定索引值,我想获取前 100 行的平均“覆盖率”值。例如,对于索引位置 1001,我想要第 901-1000 行的平均“
import pandas as pd data = {'date': ['1998-03-01', '2001-04-01','1998-06-01','2001-08-01','2001-05-0
我有一个包含 100 个数字的 NSArray。我想创建一个 5 个数字的 NSArray。第二个数组中的第一个数字是第一个数组中前 20 个数字的平均值。第二个数字是第一个数组中第二组 20 个数字
我该怎么做?我试过 abs() 但它只适用于整数。有内置的方法吗? CGFloat flo = -123; abs(flo) 返回 0 最佳答案 使用 fabs() CGFloat f = -123.
我正在采用以下计算的 log2: tl_out.a.bits.size := log2Ceil(s1_row * s2_column * 4.U) 其中,s1_row 和 s2_column 是 UI
如何从 m 个元素集合中取出 n 个元素,以便在元素用完时从头开始? List list = new List() {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; List newL
我已经完成了研究,但似乎找不到有关该主题的足够文档。 在 Object streams 上尝试一些代码时,我注意到将 BufferedOutputStream 放入 ObjectOutputStrea
我需要计算数据中连续时间组之间的差异,如下所示 from io import StringIO import pandas as pd strio = StringIO("""\
我在 Mongo 数据库中有以下文档: { _id: 1, question: "Blue or red?", __v: 0, votes: [9, 5] } 我想在后
好吧,宇宙中一定有人知道这个问题的答案。 我已经在这里问过这个问题,但仍然没有解决方案。 我需要保留和换行 div 中的文本。到目前为止,我很难想出解决方案。我找到的最佳解决方案并不适用于所有浏览器。
我正在尝试采用 3 个单独的整数输入(年、月、日)并采用这 3 个条目并从中形成一个日期对象,以便我可以使用它来比较其他日期。 这是我目前所拥有的,不知从何而来: public void compar
在我的 IOS 项目中,我有一个包含该函数的自定义 Logger 类(单例) - (void)log:(NSString *)domain logLevel:(int)level logMessage
我是一名优秀的程序员,十分优秀!