字符串在Python内部的表示是unicode编码,所以,在作编码转换时,一般须要以unicode做为中间编码,即先将其余编码的字符串解码(decode)成unicode,再从unicode编码(encode)成另外一种编码。html
decode的做用是将其余编码的字符串转换成unicode编码,如str1.decode('gb2312'),表示将gb2312编码的字符串str1转换成unicode编码。 python
encode的做用是将unicode编码转换成其余编码的字符串,如str2.encode('gb2312'),表示将unicode编码的字符串str2转换成gb2312编码。 linux
所以,转码的时候必定要先搞明白,字符串str是什么编码,而后decode成unicode,而后再encode成其余编码 正则表达式
(与代码自己的编码是一致的!)
测试:
个人eclipse里面代码为utf-8编码的。而后我这样写代码
s="你好"
s=s.decode('gb2312').encode('utf-8')
print s
报错:
UnicodeDecodeError: 'gb2312' codec can't decode bytes in position 2-3: illegal multibyte sequence
缘由:由于个人文件为UTF-8编码的。因此你想用gb2312将其转成unicode是不可能的。
因此正确的写法应当是:
s="你好"
print s
s=s.decode('utf-8').encode('utf-8') 要用UTF-8来作编码
print s
哈哈发现打印出来的是乱码那只能说明一件事情就是个人eclipse控制台是GB2312的编码!
请看:
如何得到系统的默认编码?
#!/usr/bin/env python
#coding=utf-8
import sys
print sys.getdefaultencoding()
该段程序在英文WindowsXP上输出为:ascii 。我发现个人linux上面也是ascii编码。因此我想打印出来看到的乱码是正常的。由于我实际上是utf-8编码的。
在某些IDE中,字符串的输出老是出现乱码,甚至错误,实际上是因为IDE的结果输出控制台自身不能显示字符串的编码,而不是程序自己的问题。(是的。个人eclipse控制台就是gb2312的编码因此我文件保存为utf-8的时候而后再经过打印是乱码了!)
一、读文件命令确定是:
myfile = codecs.open("c.html","r","utf-8") 由于我用gb2312来读的话报错
心得:检查一个字符串是什么编码只须要看一下decode 若是用gb2312来decode没报错的话就表示是gb2312
若是用utf-8来decode没有报错的话就表示是utf-8
如今遇到一个问题就是
请看:
myfile = codecs.open("c.html","r","utf-8")
str = myfile.read()
content = str.replace("\n"," ")
content = content.encode('utf-8')
print content
没有报错
再看:
myfile = codecs.open("c.html","r","utf-8")
str = myfile.read() #显示中文
content = str.replace("\n"," ")
content = content.encode('gb2312') 用gb2312
print content
报错:UnicodeEncodeError: 'gb2312' codec can't encode character u'\u2014' in position 12628
再看:
myfile = codecs.open("d.html","r","utf-8")
str = myfile.read() #显示中文
content = str.replace("\n"," ")
content = content.encode('gb2312') 用gb2312
print content
没问题
myfile = codecs.open("d.html","r","utf-8")
str = myfile.read() #显示中文
content = str.replace("\n"," ")
content = content.encode('utf-8')
print content
也没问题
结论:我想是c.html页面里面 存在某些 特殊字符 只支持utf-8编码。而不支持gb2312的编码!
而d.html没有这种特殊字符。这也就解释了为何
有的文件并无发生咱们想像中的问题!
因此我感受打开文件确定是用utf-8来读取获得一个unicode编码值!
而后对其作utf-8的编码处理。由于若是你作gb2312处理的话就会报错了!
接着:
我看了一下个人正则表达式发现若是用gb2312作解码处理的话同样会报错。因此判定确定是utf-8编码了!
regex3 = regex3.decode('utf-8')
print type(regex3) #返回为unicode码了!
print regex3 #竟然打印为正常的中文显示了 奇怪
尝试解决办法:
一、所有用unicode处理
即正则我用regex3 = regex3.decode('utf-8') 将其处理成 unicode编码了。而后内容也
print type(content) 也是unicode编码。结果仍是不行!
难道是个人linux终端的编码引发的吗?我看了一下
locale 发现是GBK的终端的。即只有GBK编码才能显示出来为中文的!
因而我将
regex3 = regex3.decode('utf-8').encode('gb2312') 编码成gb2312结果能够显示中文!
OK。我又将个人内容也一块儿弄成GB2312
content = content.encode('gb2312','ignore')
print content 也能够成功打印出来中文。
我想这个时候应该没有什么问题了吧。结果一用正则又死掉了。昏死!!!!!!!
换另一个好的文件测试下看看:换了以后发现没死并且成功了!
因此我以为:确定是这个文件里面的某些内容与正则匹配出现了冲突!致使的!
继续跟踪:
出现以下的状况
myfile = codecs.open("01.htm","r","utf-8","ignore")
str = myfile.read()
content = str.replace("\n"," ")
print type(content) #发现是unicode码
regex3 = 'class=wpcpsCSS>([^<]+)(?:.*?wpcppb_CSS> ([0-9]+) </span>)?.*?(?:.*?(已被关闭))?.*?([0-9]+)个回答.*?([0-9]+)次浏览.*?(?:<div class=wpcptfCSS>.*?user\?userid=([0-9]+).*?>(.*?)</a> </div>.*?)?(?:user\?userid=([0-9]+)")? class="wpfitCSS[^"]+">([^<]+).*?class=wpcptsCSS>([^<]+).*?([0-9.]{9,}\*).*?class=wpcpdCSS>(.*?)</div> <div class=wpcpfCSS>'
content = content.encode('utf-8')
p=re.compile(regex3)
results = p.findall(content)
没有什么问题能够成功出来结果。可是我
将content = content.encode('gb2312') 的话就发现 死掉了!
说明个人内容content与个人正则的编码实际上是不同的!
我如今将个人正则也调成gb2312来测试。结果发现能够出来。并且个人结果
results = p.findall(content)
for ele in results:
print ele[0],ele[1],ele[2],ele[3],ele[4],ele[5],ele[6],ele[7],ele[8],ele[9],ele[10]
在eclipse(默认为gb2312)下面也是没有问题的了!~
因此我想:若是content是GBK那正则的内容也应当是GBK 即二者的编码必定要保持一致!不然就会出现死掉程序的状况!
如今我这样来处理
所有使用unicode编码处理
myfile = codecs.open("right.html","r")
str = myfile.read()
content = str.replace("\n"," ")
content = content.decode('utf-8','ignore') #使用utf-8解码出来
都使用unicode编码吧
如今正则也用
regex3 = regex3.decode('utf-8','ignore') 使用utf-8搞成unicode编码
OK如今再来测试!
结论:
解决正则出现中文的BUG结论:
一、打开文件
myfile = codecs.open("right.html","r")
不须要设置其编码的!
设置编码格式
str = myfile.read()
content = str.replace("\n"," ")
content = content.decode('utf-8','ignore') #使用utf-8解码成unicode格式
正则:
regex3 = regex3.decode('utf-8','ignore') #正则也统一使用utf-8解码成unicode格式
而后就能够
p=re.compile(regex3)
results = p.findall(content)
调用正则了! eclipse