1.arrow
Arrow提供了一个合理的、人性化的方法来创建、操作、格式转换的日期,时间,和时间戳,帮助我们使用较少的导入和更少的代码来处理日期和时间。
安装
pip install arrow
常用方法案例:
# -*- coding: utf-8 -*-
import arrow
'''1.获取当前时间'''
print(arrow.utcnow()) # 获取当前utc时间
print(arrow.now()) # 获取当前系统时间
'''2.将时间戳转化为arrow对象 时间戳可以是int,float或者可以转化为float的字符串'''
print(arrow.get(1556073222))
print(arrow.get('1556073222'))
print(arrow.get(1556073222.264))
print(arrow.get('1556073222.264'))
'''将字符串转换为arrow对象 arrow.get(string[,format_string])'''
print(arrow.get('2019-04-24 10:43:30','YYYY-MM-DD HH:mm:ss'))
print(arrow.get('2019-04-24T10:00:00.000-07:00')) # 循ISO-8601的字符串不需要格式字符串参数即可转换
print(arrow.get('June was born in December 1994', 'MMMM YYYY')) # 可以从字符串中通过格式参数搜索时间
print(arrow.get(2019, 4, 24)) # 直接创建arrow对象
print(arrow.Arrow(2019, 4, 24)) # 直接创建arrow对象
'''arrow对象属性 datetime,timestamp,tzinfo'''
time_msg = arrow.now()
print(time_msg.datetime)
print(time_msg.timestamp) # 时间戳
print(time_msg.naive)
print(time_msg.tzinfo) # 时区
print(time_msg.hour) # 小时
print(time_msg.day) # 日期(天)
'''时间推移 a.shift(**kwargs)'''
print(time_msg.shift(days=-1)) # 前一天
print(time_msg.shift(weeks=+1)) # 一周后
print(time_msg.shift(weekday=6)) # 距离time_msg最近的一个星期日,weekday从0到6代表周一到周日
'''时间替换 a.replace(**kwargs)'''
print(time_msg.replace(hour=6)) # 将小时替换为6
'''格式化输出 a.format([format_string])'''
print(time_msg.format())
print(time_msg.format('YYYY-MM-DD HH:mm:ss ZZ'))
2. toolz
安装
pip install toolz
案例
# -*- coding:utf-8 -*-
'''
1.纯函数
(1).它不依赖于隐藏状态,或等效的取决于它的输入。
(2).功能评估不会引起副作用
简而言之,纯函数的内部工作与程序的其余部分是隔离的。
'''
# 纯函数
def min(x,y):
if x<y:
return x
else:
return y
# 非纯函数
exponent = 2
def powers(L):
for i in range(len(L)):
L[i] = L[i]**exponent
return L
if __name__ == '__main__':
result1 = min(6,10)
data = [1,2,3]
result2 = powers(data)
print(result1)
print(result2)
# min()函数的功能很纯粹,在给定相同输入参数的情况下,它的产生的结果始终是相同的。
# powers()函数的输出结果是受到全局变量exponent影响的,因此是不纯的。
'''
2.惰性迭代器
惰性迭代器仅在必要时进行评估。它们允许我们在语义上操作大量数据,同时在内存中
保留很少的数据。它们像列表一样,但不占用空间。
'''
# 打开一个文件,python打开这个文件,但是不读取任何一行文本,对象book就是一个惰性迭代器。
# 当我们调用next()读取文件内容时,book迭代器会在文本中慢慢前进
book = open('book_of_tools.txt')
print(next(book)) # 第一行
print(next(book)) # 下一行
# 我们可以懒惰地操作惰性迭代器而不进行任何实际计算
from toolz import map
loud_book = map(str.upper,book)
print(next(loud_book)) # 第一行
print(next(loud_book)) # 下一行
# 我们经常使用懒惰来避免一次将大数据集加载到内存中。对大型数据集的许多计算不需要一次访问所有数据。
# 如下是计算文本中的所有字母。
from toolz import concat, frequencies
letters = frequencies(concat(loud_book))
print(letters)
'''
3.Curry
curried函数部分评估它是否没有收到足够的参数来计算结果
'''
from toolz import curry
@curry
def mul(x,y):
return x*y
double = mul(2,2)
print(double)
3. peewee
安装
pip install peewee
案列
# -*- coding:utf-8 -*-
from peewee import *
'''
Peewee 是一个简单、轻巧的 Python ORM。
简单、轻巧、富有表现力(原词 expressive )的ORM
支持python版本 2.6+ 和 3.2+
支持数据库包括:sqlite, mysql and postgresql
包含一堆实用的扩展在 playhouse 模块中
'''
'''
1.模型定义
宾语 对应...
模型类 数据库表
字段实例 在桌子上的列
模型实例 在数据库表中的行
'''
db = SqliteDatabase('people.db')
# 创建Person模型类
class Person(Model):
name = CharField()
birthday = DateField()
class Meta:
database = db
# 创建Pet模型类
class Pet(Model):
owner = ForeignKeyField(Person,backref='pets')
name = CharField()
animal_type = CharField()
class Meta:
database = db
# 创建数据存储标表
db.create_tables([Person,Pet])
'''
2.存储数据
通过save()和create()方法添加和更新记录
'''
from datetime import date
old_wang = Person(name='wangyifan', birthday=date(1994,12,15))
old_wang.save()
# 使用create()方法添加人员
old_zhao = Person.create(name='zhaoyi', birthday=date(1996,3,13))
old_liu = Person.create(name='liuxing', birthday=date(1995,2,23))
# 更新数据时,可修改模型实例后调用save()方法保存更改
old_zhao.name = 'zhaoxue'
old_zhao.save() # 保存修改
print(old_zhao.name)
# 为人员分配宠物
wang_lucky = Pet.create(owner=old_wang, name='lucky', animal_type='dog')
zhao_ww = Pet.create(owner=old_zhao, name='ww', animal_type='dog')
# 删除宠物
zhao_ww.delete_instance()
# 将宠物分配给其他人
wang_lucky.owner = old_zhao
wang_lucky.save()
print(wang_lucky.owner.name)
'''3.数据检索'''
# 从数据库获取单个记录 select.get()
person_a = Person.select().where(Person.name == 'wangyifan').get()
print(person_a.name,"person_a.name")
person_a = Person.get(Person.name == 'wangyifan') # 简化写法
print(person_a.name,"person_a.name,")
# (1)记录列表
for person in Person.select(): # 列出数据库中的所有人
print(person.name)
dog_list = Pet.select().where(Pet.animal_type == 'dog') # 列出所有狗及其主人的名字
for dog in dog_list:
print(dog.name, dog.owner.name)
# (2)获取wangyifan拥有的所有宠物
for pet in Pet.select().join(Person).where(Person.name == 'wangyifan'):
print(pet.name)
# (3)排序 order_by()
for pet in Pet.select().where(Pet.owner == old_wang).order_by(Pet.name): # 列出宠物按姓名排序
print(pet.name)
for person in Person.select().order_by(Person.birthday.desc()): # 列出所有人,从年轻到年长
print(person.name, person.birthday)
#(4) 组合过滤器表达式
d1995 = date(1995, 3, 1)
d1996 = date(1996, 1, 1)
# 生日小于1995大于1996 两个日期直接可以用Person.birthday.between(d1940, d1960)
person_list = (Person.select().where((Person.birthday < d1995) | (Person.birthday > d1996)))
for person in person_list:
print(person.name, person.birthday)
# (5)聚合和预取
for person in Person.select():
print(person.name, person.pets.count(), 'pets')
'''4.数据库'''
# 关闭连接
db.close()
# 使用现有数据库,如已有数据库,则可以使用模型生成器pwiz自动生成peewee模型 。
# 例如,有一个名为charles_blog的postgresql数据库 ,则可以执行如下命令
# python -m pwiz -e postgresql charles_blog > blog_model.py
4.pymysql
安装
pip install PyMySQL
案例
# -*- coding:utf-8 -*-
import pymysql
'''1.数据库查询操作'''
db = pymysql.connect("localhost","root","root","hd_20190424") # 地址,用户名,密码,数据库名
# 使用cursor()方法创建一个游标对象 cursor
cursor = db.cursor()
# 使用execute()方法执行sql语句
cursor.execute("select version()")
# 使用fetchone()方法获取单条数据
data = cursor.fetchone()
print("database version:%s" % data)
# 关闭数据库连接
db.close()
'''2.数据库插入操作'''
import pymysql
# 打开数据库连接
db = pymysql.connect("localhost","root","root","hd_20190424")
# 使用cursor()方法获取操作游标
cursor = db.cursor()
# SQL 插入语句
sql = """INSERT INTO hd_20190424(username,age)VALUES ('wangyifan', 25)"""
try:
# 执行sql语句
cursor.execute(sql)
# 提交到数据库执行
db.commit()
except:
# 如果发生错误则回滚
db.rollback()
# 关闭数据库连接
db.close()
5.PyYAML
安装
pip install pyyaml
案例
# -*- coding:utf-8 -*-
import yaml
# 加载YAML
yaml_obj = yaml.load("""- Hesperiida
- Papilionidae
- Apatelodidae
- Epiplemidae""")
print (yaml_obj)
# PyYAML允许您构造任何类型的Python对象。
yaml_obj2 = yaml.load("""
none:[~,null]
bool:[True,False,on,off]
int:33
float:3.1415926
list:[wangyifan,1,'ddd']
dic:[name:wang,age:25]
""")
print(yaml_obj2)
# 倾倒YAML
print yaml.dump({'name': 'Silenthand Olleander', 'race': 'Human', 'traits': ['ONE_HAND', 'ONE_EYE']})
#打开并显示yaml文件内容
import yaml
f=open('yaml_data.ini')
data=yaml.load(f)
print data,'=========data'
#将Python对象写入yaml文件
f=open('data.yaml','w')
data={
'name': 'Silenthand Olleander',
'race': 'Human',
'traits': ['ONE_HAND', 'ONE_EYE']
}
yaml.dump(data,f)
6.* requests
安装
pip install requests
案例
# -*- coding:utf-8 -*-
import requests
'''1.get请求'''
# 请求
r = requests.get('https://www.baidu.com')
# 传参
params_data = {'wd':'wangyifan'}
r = requests.get('https://www.baidu.com', params=params_data)
print(r.url) # 访问地址
print(r.text) # 获取网页文本 返回的是Unicode型的数据 Unicode
print(r.content) #获取网页文本 返回的是bytes型也就是二进制的数据。 str
# print(r.json()) # 如果获取的是json数据的话
print(r.status_code) # 状态
r = requests.get('https://www.baidu.com',stream=True)
print(r.raw) # 返回原始socket respons,需要加参数stream=True
print(r.raw.read(10),'====')
print(r.cookies,'===')
'''2.POST请求'''
# 请求
r = requests.post('http://httpbin.org/post', data = {'key':'value'})
# 参数
data_msg = {'key1': 'value1', 'key2': 'value2'}
r = requests.post("http://httpbin.org/post", data=data_msg)
print(r.text)
print(r.cookies)
# 文件传递
url = 'http://httpbin.org/post'
files = {'file': open('report.xls', 'rb')}
r = requests.post(url, files=files)
# session
# session对象能够帮我们跨请求保持某些参数,也会在同一个session实例发出的所有请求之间保持cookies。
s = requests.Session() # 创建一个session对象
s.get('http://httpbin.org/cookies/set/sessioncookie/123456789')
r = s.get('http://httpbin.org/cookies')
print(r.text,'==========')
7.* PyStaticConfiguration
安装
# -*- coding:utf-8 -*-
import staticconf
'''
1.staticconf是一个库,用于从许多异构格式加载配置值并读取这些值。
该过程分为两个阶段(配置加载和读取配置值)。
'''
# 案例,给定两个文件
# application.yaml
'''
pid : /var/run/app1.pid
storage_paths :
- / mnt / storage
- / mnt / nfs
min_date : 2014-12-12
groups :
users :
- userone
- usertwo
admins :
- admin
'''
# overrides.yaml
'''
max_files: 10
groups:
users:
- customuser
'''
# 加载配置
import staticconf
app_config = 'application.yaml'
app_custom = 'overrides.yaml'
staticconf.YamlConfiguration(app_config)
staticconf.YamlConfiguration(app_custom, optional=True) # 覆盖app_config中的配置
# 读取配置
import staticconf
pid = staticconf.read_string('pid')
storage_paths = staticconf.read_list_of_string('storage_paths')
users = staticconf.read_list_of_string('groups.users')
admins = staticconf.read_list_of_string('groups.admins')
min_date = staticconf.read_date('min_date')
print(pid)
print(storage_paths)
print(users)
print(admins)
print(min_date)
'''2.readers'''
# 例子 read an int
import staticconf
config = staticconf.NamespaceReaders('bling')
max_cycles = config.read_int('max_cycles')
ratio = config.read_float('ratio')
'''3.Schemas'''
from staticconf import schema
class SomethingUsefulSchema(schema.Schema):
namespace = 'useful_namespace'
config_path = 'useful'
max_value = schema.int(default=100)
ratio = schema.float()
msg = schema.any(config_key='msg_string', default="Welcome")
config = SomethingUsefulSchema()
print config.msg
'''4.getters'''
import staticconf
# Returns a ValueProxy which can be used just like an int
max_cycles = staticconf.get_int('max_cycles')
print "Half of max_cycles", max_cycles / 2
# 对象从命名空间使用NamespaceGetters对象
config = staticconf.NamespaceGetters('special')
ratio = config.get_float('ratio')
案例
8.* jinja2
安装
pip install jinja2
案例
# -*- coding: utf-8 -*-
from jinja2 import Template
'''1.基本API用法'''
template = Template('hello {{ name }}')
print template.render(name='wangyifan')
# 使用包加载器来加载文档的最简单的方式如下:
from jinja2 import PackageLoader, Environment
env = Environment(loader=PackageLoader('python_project', 'templates')) # 创建一个包加载器对象
template = env.get_template('bast.html') # 获取一个模板文件
template.render(name='daxin', age=18) # 渲染
'''2.jinja2基本语法 使用与Django DTL模板语法类似'''
# 1.控制结构 {% %}
# 2.变量取值 {{}}
# 3.注释{# #}
{# 这是注释 #}
{% for person in person_list %}
<p>name is {{ person.name }}</p>
{% endfor %}
'''3.继承'''
{ % extend"base.html" %} # 继承base.html文件
{ % blocktitle %} Dachenzi{ % endblock %} # 定制title部分的内容
{ % blockhead %}{{super()}} # 用于获取原有的信息
< styletype = 'text/css' >.important{color: # FFFFFF }< / style >
{ % endblock %}
'''4.过滤器'''
# safe 渲染时值不转义
# capitialize 把值的首字母转换成大写,其他子母转换为小写
# lower 把值转换成小写形式
# upper 把值转换成大写形式
# title 把值中每个单词的首字母都转换成大写
# trim 把值的首尾空格去掉
# striptags 渲染之前把值中所有的HTML标签都删掉
# join 拼接多个值为字符串
# replace 替换字符串的值
# round 默认对数字进行四舍五入,也可以用参数进行控制
# int 把值转换成整型
# 使用方式
# {{ 'abc' | upper }} >>> ABC
9.* blinker
Blinker为Python对象提供快速简单的对象到对象和广播信令。
Blinker的核心很小但提供了强大的功能:
- 命名信号的全球注册表
- 匿名信号
- 自定义名称注册表
- 永久或临时连接的接收器
- 通过弱引用自动断开接收器
- 发送任意数据有效载荷
- 从信号接收器收集返回值
- 线程安全
安装
pip install blinker
案例
# -*-coding:utf-8 -*-
from blinker import signal
'''1.创建信号'''
# 信号通过signal()方法进行创建
sig = signal("sig")
sig is signal("sig")
# 每次调用signal('name')都会返回同一个信号对象。因此这里signal()方法使用了单例模式。
'''2.订阅信号'''
# 使用Signal.connect()方法注册一个函数,每当触发信号的时候,就会调用该函数。
# 该函数以触发信号的对象作为参数,这个函数其实就是信号订阅者。
def subscriber(sender):
print('got a signal by %r' % sender)
ready = signal('ready')
print(ready.connect(subscriber))
'''3.触发信号'''
# 使用Signal.send()方法通知信号订阅者。
#下面定义类Processor,在它的go()方法中触发前面声明的ready信号,send()方法以self为参数,
# 也就是说Processor的实例是信号的发送者。
class Processor:
def __init__(self,name):
self.name = name
def go(self):
ready = signal('ready')
ready.send(self)
print("Processing.")
complete = signal('complete')
complete.send(self)
def __str__(self):
return '<Processor %s>' % self.name
def __repr__(self):
return '<Processor %s>' % self.name
processor_a = Processor('a')
processor_a.go()
10.pytest
该pytest框架可以轻松编写小型测试,然后进行扩展以支持应用程序和库的复杂功能测试。
安装
pip install -U pytest
pytest --version # 验证安装是否成功
案例
pytest_tools.py
这里我们定义了一个被测试函数func,该函数将传递进来的参数加1后返回。我们还定义了一个测试函数test_func用来对func进行测试。test_func中我们使用基本的断言语句assert来对结果进行验证。
# -*- coding:utf-8 -*-
def func(x):
return x + 1
def test_answer():
assert func(3) == 5
在命令行执行 pytest pytest_tools.py
执行测试的时候,我们只需要在测试文件test_sample所在的目录下,运行py.test即可。pytest会在当前的目录下,寻找以test开头的文件(即测试文件),找到测试文件之后,进入到测试文件中寻找test_开头的测试函数并执行。
通过上面的测试输出,我们可以看到该测试过程中,一个收集到了一个测试函数,测试结果是失败的(标记为F),并且在FAILURES部分输出了详细的错误信息,帮助我们分析测试原因,我们可以看到"assert func(3) == 5"这条语句出错了,错误的原因是func(3)=4,然后我们断言func(3) 等于 5。