设为首页 加入收藏

TOP

python使用小结
2018-12-14 02:56:24 】 浏览:103
Tags:python 使用 小结

把之前的python使用方法全部汇总到这里

python排序方法

转载自这里

C/C++与Python

C调用python接口方法

主要是参考下面两篇博文
使用c语言调用python小结
Python实例浅谈之三Python与C/C++相互调用
需要注意的是,
1.如果提示undefined reference to Py_XXXX
说明没有正确加载python的库,根据python的版本,在makefile里加入-lpython2.7
2.如果PyImport_ImportModule返回的指针为空,一定是python模块的路径搞错了,这里我开始直接给
PyImport_ImportModule的参数传的是python模块的绝对路径,返回为空。后来使用下面两句解决了问题,
应该是需要先调用第一句加入python模块的路径,PyImport_ImportModule只负责加载模块名称,不包括路径

PyRun_SimpleString("import sys");     
PyRun_SimpleString("sys.path.append('./')");   
PyImport_ImportModule('voc_eva l');  

python与c++混合编程调试方法

这里主要是调试py-faster-rcnn,其他类似
单纯使用pdb可以调试python代码,但是无法调试其调用的c++代码。
如果要调试c++代码,使用如下指令
gdb –args python test.py
具体步骤:
1.使用指令,并且r进去,让进程跑起来
2.由于此时caffe.so并没有加载进来,所以,可能会出现即使在cpp里下断点也无法跟踪的情况,这里可以先手动ctrl+c把进程断开,再设置断点,让caffe.so加载进来。
所以,这一步是下断点,如b caffe/src/caffe/solver.cpp:228
3.c,进去cpp里即可

下划线

变量

主要存在四种情形
1. object # public
2. object # special, python system use, user should not define like it
3. __object # private (name mangling during runtime)
4. _object # obey python coding convention, consider it as private
核心风格:避免用下划线作为变量名的开始。

函数

  1. 前带_的变量: 标明是一个私有函数, 只用于标明
  2. 前带两个_ ,后带两个_ 的函数: 标明是特殊函数

多层目录模块调用

转载自这里
1. 将导入模块所在目录(../model/模块)添加到系统环境变量path下,可添加多个

import sys
sys.path.append("../model")  # 模块父目录下的model文件中
from model import a

注意:不管什么样的引用,建议直接使用这种方法,避免发生引用模块里import的问题。

    (所有被引用模块的调用会优先查找当前执行目录下的文件,找不到再去找所有环境变量的目录!)

程序结构如下:

– src
|– model
| |– a.py
| |– b.py
|– test.py

a模块 调用了同级目录的b –> import b

test模块 调用a模块时出错 –> from model import a

出错:在test当前目录运行时找不到b模块。

2.引用模块在 当前目录的同级以及所包含的子目录中:
2.1. 直接import 同级文件.子文件.引用模块
2.2. from 同级文件.子文件 import 引用模块

列表等分

转载自这里
这里主要借助itertools模块里的izip和iziplongest方法,代码如下

from itertools import zip_longest    # zip_longest -> Python 3, izip_longest -> Python 2  
chunk_list = lambda a_list, n: zip_longest(*[iter(a_list)]*n)  
result_groups = list(chunk_list([x for x in range(100)], 8))  

Out[12]:   
[(0, 1, 2, 3, 4, 5, 6, 7),  
 (8, 9, 10, 11, 12, 13, 14, 15),  
 (16, 17, 18, 19, 20, 21, 22, 23),  
 (24, 25, 26, 27, 28, 29, 30, 31),  
 (32, 33, 34, 35, 36, 37, 38, 39),  
 (40, 41, 42, 43, 44, 45, 46, 47),  
 (48, 49, 50, 51, 52, 53, 54, 55),  
 (56, 57, 58, 59, 60, 61, 62, 63),  
 (64, 65, 66, 67, 68, 69, 70, 71),  
 (72, 73, 74, 75, 76, 77, 78, 79),  
 (80, 81, 82, 83, 84, 85, 86, 87),  
 (88, 89, 90, 91, 92, 93, 94, 95),  
 (96, 97, 98, 99, None, None, None, None)]  

这里借助了迭代器,关于*[iter(a_list)]*n ,参考了stackoverflow里的精彩说明,如下

iter() is an iterator over a sequence. [x]
* n produces a list containing n quantity of x, i.e. a list of length n, where each element is x. *arg unpacks a sequence into arguments for a function call. Therefore you’re passing the same iterator 3 times to zip(), and it pulls an item from the iterator each time.

x = iter([1,2,3,4,5,6,7,8,9])  
print zip(x, x, x)  

最终产生了一个等分list的方法。
等分list可以用来批量处理数据,如等分目录下的文件等。

数字前补0

转载自这里
python中有一个zfill方法用来给字符串前面补0,非常有用

n = "123"  
s = n.zfill(5)  
assert s == "00123"

zfill()也可以给负数补0

n = "-123"  
s = n.zfill(5)  
assert s == "-0123"

对于纯数字,我们也可以通过格式化的方式来补0

n = 123  
s = "%05d" % n  
assert s == "00123"

生成voc数据集的脚本代码


# !/usr/bin/env python
# -*- coding: utf-8 -*-

__author__ = 'xiaobanderui'

from xml.dom import minidom
import numpy as np
import cv2

imgpath = u'e:/VOC2007/JPEGImages/' # 图片存放路径
txtpath = u'e:/data.txt' # 保存标注信息的文件,每一行的内容为[filename objectname xmin ymin xmax ymax]
xml_path = u'e:/VOC2007/Annotations/'

lastname = u'begin'
foldername = u'VOC2007'

num = 0 # 总样本数
valid_num = 0 # 有效样本数

cv2.namedWindow('img', cv2.WINDOW_NORMAL)

with open(txtpath, 'r') as fr:
    for item in fr.readlines():
        num += 1
        print 'processing %d' % num
        item = item.strip().decode('gbk')
        str_item = item.split(' ')
        img =cv2.imread((imgpath + str_item[0]).encode('gbk'), cv2.IMREAD_UNCHANGED)
        ht. wd. cn = img.shape

        xmin = int(float(str_item[2]))
        xmax = int(float(str_item[3]))
        ymin = int(float(str_item[4]))
        ymax = int(float(str_item[5]))

        cv2.rectangle(img, (xmin, ymin), (xmax, ymax), (0, 0, 255), 2)
        cv2.imshow('img', img)
        cv2.waitKey()

        # 过滤掉标注信息错误的样本
        # 框的位置越界
        if xmin >= xmax or ymin >= ymax or xmin < 0 or ymin < 0 or xmax < 0 or ymax < 0 or xmin >= wd or xmax >= wd or ymin >= ht or ymax >= ht
            continue

        # 框的位置不对,比如翻转时
        oldx1 =xmin
        oldx2 = xmax
        newxmin = wd - oldx2 - 1
        newxmax = wd - oldx1 - 1

        if newxmin >= newxmax
            continue

         valid_num += 1

        if str_item[0] == last_name:
            object_node = doc.createElem('object')
            rootNode = doc.appendChild(object_node)

            node = doc.createElem('name')
            node_text = doc.createTextNode(str_item[1])
            node.appendChild(node_text)
            object_ode = doc.appendChild(node)

        '''
            其他类似添加,不再赘述
            '''

        else:
            if vars().has_key('rootNode'):
                fw_xml = open(xml_path + file_full_name[0] + '.xml', 'w')
                fw_xml.write(doc.toprettyxml(encoding='utf-8'))
                fw_xml.close()

            node = doc.createElem('name')
            node_text = doc.createTextNode(str_item[1])
            node.appendChild(node_text)
            object_ode = doc.appendChild(node)

    fw_xml = open(xml_path + file_full_name[0] + '.xml', 'w')
    fw_xml.write(doc.toprettyxml(encoding='utf-8'))
    fw_xml.close()

编译错误总结

代码缩进问题,错误信息如下

IndentationError: unindent does not match any outer indentation level

类型转换问题

如下字串转为int会有错误

str = '123.456'  
x = int(str) 

错误信息如下

invalid literal for int() with base 10

百度了一下,发现python里的int()只接受纯数字的转换,这里有的字串有‘.’,所以会报错,做如下更改即可

str = '123.456'  
x = round(float(str)) 

numpy

savetxt

使用numpy的savetxt保存的数据维度>=3时,会出现错误,比如保存一个三通道的数组就会出错,这里可以采用每个通道分别保存的方式

np.savetxt(filename, array[0,:,:])  
np.savetxt(filename, array[1,:,:])  
np.savetxt(filename, array[2,:,:])  

目录、文件操作

判断目录、文件是否存在

转载自这里
这篇文章主要介绍了Python判断文件和文件夹是否存在的方法,本文还讲解了判断是否为文件或者目录的方法、os.path.lexist的作用、FTP中判断文件或目录是否存在等内容,需要的朋友可以参考下
1.python判断文件和文件夹是否存在、创建文件夹,代码如下

>>> import os  
>>> os.path.exists('d:/assist')  
True  
>>> os.path.exists('d:/assist/getTeacherList.py')  
True  
>>> os.path.isfile('d:/assist')  
False  
>>> os.path.isfile('d:/assist/getTeacherList.py')  
True  
>>> os.makedirs('d:/assist/set')  
>>> os.path.exists('d:/assist/set')  
True  

2.python判断文件是否存在,代码如下

import os  

filename = r'/home/tim/workspace/test.txt'  
if os.path.exists(filename):  
    message = 'OK, the "%s" file exists.'  
else:  
    message = "Sorry, I cannot find the "%s" file."  
print message % filename 

3.如何用Python判断文件是否存在
使用os.path.exists()方法可以直接判断文件是否存在,代码如下

>>> import os  
>>> os.path.exists(r'C:\1.TXT')  
False  
>>>  

如果存在返回值为True,如果不存在则返回False
4.python判断文件夹是否存在,代码如下

$ python  
Python 2.7.3 (default, Jan  2 2013, 16:53:07)   
[GCC 4.7.2] on linux2  
Type "help", "copyright", "credits" or "license" for more information.  
>>> import os  
>>>   
>>>   
>>> tobecheckdir = r'/home/tim/workspace'  
>>> os.path.isdir(tobecheckdir)  
True  
>>>  

5.python检查文件是否存在,以及路径是否为文件

from os import path, access, R_OK  # W_OK for write permission.  
PATH='./file.txt'  
if path.exists(PATH) and path.isfile(PATH) and access(PATH, R_OK):  
    print "File exists and is readable"  
else:  
    print "Either file is missing or is not readable"  

你也可以通过下面的方式实现:

def file_exists(filename):  
    try:  
        with open(filename) as f:  
            return True  
    except IOError:  
        return False  

6.python判断文件和文件夹是否存在

import os   
os.path.isfile('test.txt') #如果不存在就返回False   
os.path.exists(directory) #如果目录不存在就返回False  

7.os.path.lexist
还有os.path.lexists(path)
对broken的link file也返回True.

8.python FTP判断文件夹是否存在
python怎样判断文件夹是否存在?广大网友给出了答案:
使用ftp库就可以了,下面是Python核心编程上的例子:

>>> from ftplib import FTP  
>>> f = FTP('ftp.python.org')  
>>> f.login('anonymous', 'guido@python.org')  
'230 Guest login ok, access restrictions apply.'  
>>> f.dir() 

dir结果中无此文件,就是不存在,或者如下:

try:  
f.retrbinary('RETR %s' % FILE,open(FILE, 'wb').write)  
except ftplib.error_perm:  
print 'ERROR: cannot read file "%s"' % FILE 40 os.unlink(FILE)  

不能读此文件,也视为不存在。

命名规范

转载自这里

常量

常量名所有字母大写,由下划线连接各个单词,如

WHITE = 0XFFFFFF
THIS_IS_A_CONSTANT = 1

变量

普通变量###

全部小写,由下划线连接各个单词,如:

color = WHITE  
this_is_a_variable = 1 

保护成员变量

单下划线作前缀,意思是只有类对象和子类对象自己能访问到这些变量,且不能用’from module import *’导入。如:

_name=name

私有成员变量

双下划线作前缀,意思是只有类对象自己能访问,连子类对象也不能访问到这个数据。

__ha=h

全局变量

大写字母,单词之间用_分割。
对于from M import *导入语句,如果想阻止导入模块内的全局变量可以使用旧有的规范,在全局变量上加一个前导的下划线

NUMBER  
COLOR_WRITE

注意:
(1) 不论是类成员变量还是全局变量,均不使用 m 或 g 前缀
(2)变量名不应带有类型信息,因为 Python 是动态类型语言。如 iValue、names_list、dict_obj 等都是不好的命名。

函数

普通函数

与普通变量一致,函数名应该为小写,可以用下划线风格单词以增加可读性。
混合大小写仅被允许用于这种风格已经占据优势的时候,以便保持向后兼容

myfunctio()  
my_example_function()  
myName()  

私有函数

以双下划线开头。如:

__get_name()

函数的参数

总使用“self”作为实例方法的第一个参数。总使用“cls”作为类方法的第一个参数。
如果一个函数的参数名称和保留的关键字冲突,通常使用一个后缀下划线好于使用缩写或奇怪的拼写。
模块:
应该是简短的、小写的名字,单词之间用_分割。模块就是指文件

hello.py  
ad_stats.py

类名单词首字母大写,不使用下划线连接单词,也不加入 C、T 等前缀
实例用小写字母

class MyClass(object)  

命名方式同模块,是文件夹
特定命名方式:xxx
主要是指 xxx 形式的系统保留字命名法。项目中也可以使用这种命名,它的意义在于这种形式的变量是只读的,这种形式的类成员函数尽量不要重载。如

class Base(object):
def __init__(self, id, parent = None):
self.__id__ = id
self.__parent__ = parent
def __message__(self, msgid):

其中 idparentmessage 都采用了系统保留字命名法。

编码问题

目前遇到的最头疼的问题,没有之一
先是一篇简要介绍,链接在这里http://in355hz.iteye.com/blog/1860787
最近业务中需要用 Python 写一些脚本。尽管脚本的交互只是命令行 + 日志输出,但是为了让界面友好些,我还是决定用中文输出日志信息。
很快,我就遇到了异常:

UnicodeEncodeError: 'ascii' codec can't encode characters in position 0-3: ordinal not in range(128)   

为了解决问题,我花时间去研究了一下 Python 的字符编码处理。网上也有不少文章讲 Python 的字符编码,但是我看过一遍,觉得自己可以讲得更明白些。

下面先复述一下 Python 字符串的基础,熟悉此内容的可以跳过。

对应 C/C++ 的 char 和 wchar_t, Python 也有两种字符串类型,str 与 unicode:

# -*- coding: utf-8 -*-    
# file: example1.py    
import string    

# 这个是 str 的字符串    
s = '关关雎鸠'    

# 这个是 unicode 的字符串    
u = u'关关雎鸠'    

print isinstance(s, str)      # True    
print isinstance(u, unicode)  # True    

print s.__class__   # <type 'str'>    
print u.__class__   # <type 'unicode'> 

前面的申明:# -- coding: utf-8 -- 表明,上面的 Python 代码由 utf-8 编码。

为了保证输出不会在 linux 终端上显示乱码,需要设置好 linux 的环境变量:export LANG=en_US.UTF-8

如果你和我一样是使用 SecureCRT,请设置 Session Options/Terminal/Appearance/Character Encoding 为 UTF-8 ,保证能够正确的解码 linux 终端的输出。

两个 Python 字符串类型间可以用 encode / decode 方法转换:

# 从 str 转换成 unicode    
print s.decode('utf-8')   # 关关雎鸠    

# 从 unicode 转换成 str    
print u.encode('utf-8')   # 关关雎鸠  

为什么从 unicode 转 str 是 encode,而反过来叫 decode

因为 Python 认为 16 位的 unicode 才是字符的唯一内码,而大家常用的字符集如 gb2312,gb18030/gbk,utf-8,以及 ascii 都是字符的二进制(字节)编码形式。把字符从 unicode 转换成二进制编码,当然是要 encode。

反过来,在 Python 中出现的 str 都是用字符集编码的 ansi 字符串。Python 本身并不知道 str 的编码,需要由开发者指定正确的字符集 decode。

(补充一句,其实 Python 是可以知道 str 编码的。因为我们在代码前面申明了 # -- coding: utf-8 --,这表明代码中的 str 都是用 utf-8 编码的,我不知道 Python 为什么不这样做。)

如果用错误的字符集来 encode/decode 会怎样?

# 用 ascii 编码含中文的 unicode 字符串    
u.encode('ascii')  # 错误,因为中文无法用 ascii 字符集编码    
                   # UnicodeEncodeError: 'ascii' codec can't encode characters in position 0-3: ordinal not in range(128)    

# 用 gbk 编码含中文的 unicode 字符串    
u.encode('gbk')  # 正确,因为 '关关雎鸠' 可以用中文 gbk 字符集表示    
                 # '\xb9\xd8\xb9\xd8\xf6\xc2\xf0\xaf'    
                 # 直接 print 上面的 str 会显示乱码,修改环境变量为 zh_CN.GBK 可以看到结果是对的    

# 用 ascii 解码 utf-8 字符串    
s.decode('ascii')  # 错误,中文 utf-8 字符无法用 ascii 解码    
                   # UnicodeDecodeError: 'ascii' codec can't decode byte 0xe5 in position 0: ordinal not in range(128)    

# 用 gbk 解码 utf-8 字符串    
s.decode('gbk')  # 不出错,但是用 gbk 解码 utf-8 字符流的结果,显然只是乱码    
                 # u'\u934f\u51b2\u53e7\u95c6\u5ea8\u7b2d'    

这就遇到了我在本文开头贴出的异常:UnicodeEncodeError: ‘ascii’ codec can’t encode characters in position 0-3: ordinal not in range(128)

现在我们知道了这是个字符串编码异常。接下来, 为什么 Python 这么容易出现字符串编/解码异常?

这要提到处理 Python 编码时容易遇到的两个陷阱。第一个是有关字符串连接的:

# -*- coding: utf-8 -*-    
# file: example2.py    

# 这个是 str 的字符串    
s = '关关雎鸠'    

# 这个是 unicode 的字符串    
u = u'关关雎鸠'    

s + u  # 失败,UnicodeDecodeError: 'ascii' codec can't decode byte 0xe5 in position 0: ordinal not in range(128)  

简单的字符串连接也会出现解码错误?

陷阱一:在进行同时包含 str 与 unicode 的运算时,Python 一律都把 str 转换成 unicode 再运算,当然,运算结果也都是 unicode。

由于 Python 事先并不知道 str 的编码,它只能使用 sys.getdefaultencoding() 编码去 decode。在我的印象里,sys.getdefaultencoding() 的值总是 ‘ascii’ ——显然,如果需要转换的 str 有中文,一定会出现错误。

除了字符串连接,% 运算的结果也是一样的:

# 正确,所有的字符串都是 str, 不需要 decode    
"中文:%s" % s   # 中文:关关雎鸠    

# 失败,相当于运行:"中文:%s".decode('ascii') % u    
"中文:%s" % u  # UnicodeDecodeError: 'ascii' codec can't decode byte 0xe5 in position 0: ordinal not in range(128)    

# 正确,所有字符串都是 unicode, 不需要 decode    
u"中文:%s" % u   # 中文:关关雎鸠    

# 失败,相当于运行:u"中文:%s" % s.decode('ascii')    
u"中文:%s" % s  # UnicodeDecodeError: 'ascii' codec can't decode byte 0xe5 in position 0: ordinal not in range(128)   

我不理解为什么 sys.getdefaultencoding() 与环境变量 LANGPython<script type="math/tex" id="MathJax-Element-3">LANG 全无关系。如果 Python 用 LANG 设置 sys.getdefaultencoding() 的值,那么至少开发者遇到 UnicodeDecodeError 的几率会降低 50%。

另外,就像前面说的,我也怀疑为什么 Python 在这里不参考 # -- coding: utf-8 -- ,因为 Python 在运行前总是会检查你的代码,这保证了代码里定义的 str 一定是 utf-8 。

对于这个问题,我的唯一建议是在代码里的中文字符串前写上 u。另外,在 Python 3 已经取消了 str,让所有的字符串都是 unicode ——这也许是个正确的决定。

其实,sys.getdefaultencoding() 的值是可以用“后门”方式修改的,我不是特别推荐这个解决方案,但是还是贴一下,因为后面有用:

# -*- coding: utf-8 -*-    
# file: example3.py    
import sys    

# 这个是 str 的字符串    
s = '关关雎鸠'    

# 这个是 unicode 的字符串    
u = u'关关雎鸠'    

# 使得 sys.getdefaultencoding() 的值为 'utf-8'    
reload(sys)                      # reload 才能调用 setdefaultencoding 方法    
sys.setdefaultencoding('utf-8')  # 设置 'utf-8'    

# 没问题    
s + u  # u'\u5173\u5173\u96ce\u9e20\u5173\u5173\u96ce\u9e20'    

# 同样没问题    
"中文:%s" % u   # u'\u4e2d\u6587\uff1a\u5173\u5173\u96ce\u9e20'    

# 还是没问题    
u"中文:%s" % s  # u'\u4e2d\u6587\uff1a\u5173\u5173\u96ce\u9e20'    

可以看到,问题魔术般的解决了。但是注意! sys.setdefaultencoding() 的效果是全局的,如果你的代码由几个不同编码的 Python 文件组成,用这种方法只是按下了葫芦浮起了瓢,让问题变得复杂。

另一个陷阱是有关标准输出的。

刚刚怎么来着?我一直说要设置正确的 linux LANG<script type="math/tex" id="MathJax-Element-4">LANG 环境变量。那么,设置错误的 LANG,比如 zh_CN.GBK 会怎样?(避免终端的影响,请把 SecureCRT 也设置成相同的字符集。)

显然会是乱码,但是不是所有输出都是乱码。

# -*- coding: utf-8 -*-    
# file: example4.py    
import string    

# 这个是 str 的字符串    
s = '关关雎鸠'    

# 这个是 unicode 的字符串    
u = u'关关雎鸠'    

# 输出 str 字符串, 显示是乱码    
print s   # 鍏冲叧闆庨笭    

# 输出 unicode 字符串,显示正确    
print u  # 关关雎鸠    

为什么是 unicode 而不是 str 的字符显示是正确的? 首先我们需要了解 print。与所有语言一样,这个 Python 命令实际上是把字符打印到标准输出流 —— sys.stdout。而 Python 在这里变了个魔术,它会按照 sys.stdout.encoding 来给 unicode 编码,而把 str 直接输出,扔给操作系统去解决。

这也是为什么要设置 linux $LANG 环境变量与 SecureCRT 一致,否则这些字符会被 SecureCRT 再转换一次,才会交给桌面的 Windows 系统用编码 CP936 或者说 GBK 来显示。

通常情况,sys.stdout.encoding 的值与 linux $LANG 环境变量保持一致:

# -*- coding: utf-8 -*-    
# file: example5.py    
import sys    

# 检查标准输出流的编码    
print sys.stdout.encoding  # 设置 $LANG = zh_CN.GBK,  输出 GBK    
                           # 设置 $LANG = en_US.UTF-8,输出 UTF-8    

# 这个是 unicode 的字符串    
u = u'关关雎鸠'    

# 输出 unicode 字符串,显示正确    
print u  # 关关雎鸠    

但是,这里有 陷阱二:一旦你的 Python 代码是用管道 / 子进程方式运行,sys.stdout.encoding 就会失效,让你重新遇到 UnicodeEncodeError。

比如,用管道方式运行上面的 example4.py 代码:

python -u example5.py | more    

UnicodeEncodeError: 'ascii' codec can't encode characters in position 0-3: ordinal not in range(128)    
None    

可以看到,第一:sys.stdout.encoding 的值变成了 None;第二:Python 在 print 时会尝试用 ascii 去编码 unicode.

由于 ascii 字符集不能用来表示中文字符,这里当然会编码失败。

怎么解决这个问题? 不知道别人是怎么搞定的,总之我用了一个丑陋的办法:

# -*- coding: utf-8 -*-    
# file: example6.py    
import os    
import sys    
import codecs    

# 无论如何,请用 linux 系统的当前字符集输出:    
if sys.stdout.encoding is None:    
    enc = os.environ['LANG'].split('.')[1]    
    sys.stdout = codecs.getwriter(enc)(sys.stdout)  # 替换 sys.stdout    

# 这个是 unicode 的字符串    
u = u'关关雎鸠'    

# 输出 unicode 字符串,显示正确    
print u  # 关关雎鸠    

这个方法仍然有个副作用:直接输出中文 str 会失败,因为 codecs 模块的 writer 与 sys.stdout 的行为相反,它会把所有的 str 用 sys.getdefaultencoding() 的字符集转换成 unicode 输出。

# 这个是 str 的字符串    
s = '关关雎鸠'    

# 输出 str 字符串, 异常    
print s   # UnicodeDecodeError: 'ascii' codec can't decode byte 0xe5 in position 0: ordinal not in range(128)   

显然,sys.getdefaultencoding() 的值是 ‘ascii’, 编码失败。

解决办法就像 example3.py 里说的,你要么给 str 加上 u 申明成 unicode,要么通过“后门”去修改 sys.getdefaultencoding():

# 使得 sys.getdefaultencoding() 的值为 'utf-8'    
reload(sys)                      # reload 才能调用 setdefaultencoding 方法    
sys.setdefaultencoding('utf-8')  # 设置 'utf-8'    

# 这个是 str 的字符串    
s = '关关雎鸠'    

# 输出 str 字符串, OK    
print s   # 关关雎鸠  

总而言之,在 Python 2 下进行中文输入输出是个危机四伏的事,特别是在你的代码里混合使用 str 与 unicode 时。

有些模块,例如 json,会直接返回 unicode 类型的字符串,让你的 % 运算需要进行字符解码而失败。而有些会直接返回 str, 你需要知道它们的真实编码,特别是在 print 的时候。

为了避免一些陷阱,上文中说过,最好的办法就是在 Python 代码里永远使用 u 定义中文字符串。另外,如果你的代码需要用管道 / 子进程方式运行,则需要用到 example6.py 里的技巧。

后来,为了统一Windows和Linux上的编码,不管什么字符串,我都会在前面加上u,把它们全部强制转化为Unicode。但是,在打印类似list和dict这些数据结构的时候,显示中文字符遇到了问题,只能显示unicode编码,无法显示中文。
解决办法转载自这里http://blog.csdn.net/xiaobei4929/article/details/38734047
在从元组转换到字符串时,中文字符前会出现u’例子’类似这种,具体可参考第二个文章,需要手动去除u一切就都正常了

[u'\u773c', u'\u8179\u90e8', u'\u4e94\u5b98', u'\u53e3\u8154', u'\u8179\u90e8',  
u'\u53e3\u8154'] 
str_symptom = str(all_symptom).replace('u\'','\'')  
str_symptom.decode("unicode-escape") 
['眼', '腹部', '五官', '口腔', '腹部', '口腔']  #处理后的显示情况

另外,对于dict这种无序表,可以使用OrderedDict来代替,具体可以参考廖雪峰的python教程,非常棒

其他的一些小结

这里有一个爱可可老师的分享python-snippets

类与属性

参考这篇博客
主要是这句话有用

getattr(object, name[,default])
获取对象object的属性或者方法,如果存在打印出来,如果不存在,打印出默认值,默认值可选。
需要注意的是,如果是返回的对象的方法,返回的是方法的内存地址,如果需要运行这个方法,
可以在后面添加一对括号。

multiprocessing里的Process模块,多线程调用非常的恶心,有些错误,即使添加了print还是无法达到追踪的效果,有时只能改掉多线程的调用方式

列表、字典

使用list初始化dict的方法是

d=dict.fromkeys(l, 0)

得到一个值全为0的字典
对于字典而言,dict[‘x’] =1的操作,如果dict中没有’x’这个键,那么这时就会创建1个新的item

】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇python 学习第一天 下一篇ubuntu系统用pyenv实现python多版..

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目