![300528ce872d1a3bde77d5d447de44f2.png](https://i-blog.csdnimg.cn/blog_migrate/7427582a7943c8185858e634d709ce77.jpeg)
读写CSV数据
对于大部分的CSV数据,我们都可以用csv库来进行处理,举个例子,假设我们在名为stocks.csv的文件中有这样的数据:
('AA', 39.48, '6/11/2007', '9:36am', -0.18, 181800),
('AIG', 71.38, '6/11/2007', '9:36am', -0.15, 195500),
('AXP', 62.58, '6/11/2007', '9:36am', -0.46, 935000),
于是我们把这些数据读取为元组序列
import csv
from collections import namedtuple
def rw_csv():
with open('stocks.csv') as f:
f_csv = csv.reader(f)
headers = next(f_csv)
for row in f_csv:
print(row)
在上面的代码里面,row会是一个元组,因此,想要访问特定的字段就需要用到索引,而又由于这样的索引很容易产生混淆,建议还是将元组进行命名。这样就可以使用每一列的标头比如row.Symbol和row.Change来取代之前的索引了。但是这个方法也只有在每一列的标头都是合法Python标识符的时候才适用。如果不是的话,我们就必须要调整原始标头。
当然,你也可以像我上面那样把数据读取为字典序列。在Python3中,我们可以通过行表头来访问每行中的元素,如果我们想写入csv数据,就用csv模块来创建一个写入对象来进行写入:
headers = ['Symbol', 'Price', 'Date', 'Time', 'Change', 'Volume']
rows = [('AA', 39.48, '6/11/2007', '9:36am', -0.18, 181800),
('AIG', 71.38, '6/11/2007', '9:36am', -0.15, 195500),
('AXP', 62.58, '6/11/2007', '9:36am', -0.46, 935000),
]
with open('stocks.csv', 'w') as f:
f_csv = csv.writer(f)
f_csv.writerow(headers)
f_csv.writerows(rows)
在默认情况下,csv库被实现为能够识别微软的Excel所采用的CSV编码规则,也就是说,csv库的兼容性非常好的。但是,如果你认真看了CSV的文档,你就会发现,其实你还有几种方法可以将编码调成其它格式。
此外csv模块并不会尝试去解释数据或者将数据转换为除了字符串之外的类型,如果你想进行转换,你必须自己手动来:
col_types = [str, float, str, str, float, int]
with open('stocks.csv') as f:
f_csv = csv.reader(f)
headers = next(f_csv)
for row in f_csv:
row = tuple(convert(value) for convert, value in zip(col_types, row))
读取JSON数据
在json模块中提供了一种简单的方法来编码和解码json格式的数据,这两个主要的函数就是json.dumps()以及json.loads()。这两个函数在命名上借鉴了其它序列化处理库的接口,比如说pickle。
当然,如果要同文件而不是字符串打交道的话,可以选择使用json.dump()以及json.load()来编码和解码json数据。实际操作如下:
import json
from collections import OrderedDict
class JSONObject:
def __init__(self, d):
self.__dict__ = d
class Point:
def __init__(self, x, y):
self.x = x
self.y = y
def serialize_instance(obj):
d = {'__classname__': type(obj).__name__}
d.update(vars(obj))
return d
def unserialize_object(d):
clsname = d.pop('__classname__', None)
if clsname:
cls = classes[clsname]
obj = cls.__new__(cls) # Make instance without calling __init__
for key, value in d.items():
setattr(obj, key, value)
return obj
else:
return d
# Dictionary mapping names to known classes
classes = {
'Point': Point
}
def rw_json():
data = {
'name': 'ACME',
'shares': 100,
'price': 542.23
}
json_str = json.dumps(data) # str类型
data = json.loads(json_str)
# Writing JSON data
with open('data.json', 'w') as f:
json.dump(data, f)
# Reading data back
with open('data.json', 'r') as f:
data = json.load(f)
# 使用object_pairs_hook
s = '{"name": "ACME", "shares": 50, "price": 490.1}'
data = json.loads(s, object_pairs_hook=OrderedDict)
print(data)
# 解码为自定义对象
# data = json.loads(s, object_hook=JSONObject)
# print(data.name)
# print(data.shares)
print(json.dumps(data))
print(json.dumps(data, indent=4))
p = Point(2, 3)
s = json.dumps(p, default=serialize_instance)
print(s)
a = json.loads(s, object_hook=unserialize_object)
print(a)
if __name__ == '__main__':
rw_json()
JSON编码支持None, bool, int, float和str。当然还包括这些基本类型的列表,元组和字典。对于字典,json会假设键是字符串。要符合规范,我们应该只对Python列表和字典进行编码。此外,在web应用中,把最顶层对象定义为字典是一种标准做法。
JSON编码格式和Python基本差不多,只是True,False在JSON中会被映射为true,false,而None会被映射为null。如果,你想检查从JSON中编码得到的数据,直接打印会相对来说比较困难。这个时候建议使用pprint模块中的pprint()函数,这样会把键按照字母顺序排列,并且在字典上以更加合理的方式进行输出。
参考书目:
《Python CookBook》作者:【美】 David Beazley, Brian K. Jones
Github地址:
yidao620c/python3-cookbookgithub.com![d53ce4c109b31550de061608493dea56.png](https://i-blog.csdnimg.cn/blog_migrate/633178b26ee41cd44c47a73d09ce8a93.jpeg)