Python

Python

python3: error while loading shared libraries: libpython3.5m.so.1.0

编程语言采菊篱下 回复了问题 • 2 人关注 • 1 个回复 • 105 次浏览 • 2017-09-25 17:04 • 来自相关话题

使用Ansible会提示UserWarning: Module import pkg_resources

运维技术采菊篱下 回复了问题 • 2 人关注 • 1 个回复 • 376 次浏览 • 2017-05-08 23:39 • 来自相关话题

Python操作各种数据库

编程语言采菊篱下 发表了文章 • 0 个评论 • 304 次浏览 • 2017-04-27 17:54 • 来自相关话题

我们在写代码的时候,经常会操作数据库,增删改查,数据库有很多类型,关系型数据库和非关系数据库,这里咱们介绍一下python怎么操作mysql、redis和mongodb。
 

一、操作mysql

python3中操作mysql数据需要安装一个第三方模块,pymysql,使用pip install pymysql安装即可,在python2中是MySQLdb模块,在python3中没有MySQLdb模块了,所以使用pymysql。
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()
# 执行SQL,并返回收影响行数
effect_row = cursor.execute("update students set name = 'niuhy' where id = 1;")
# 执行SQL,并返回受影响行数
#effect_row = cursor.execute("update students set name = 'niuhy' where id = %s;", (1,))
# 执行SQL,并返回受影响行数
effect_row = cursor.executemany("insert into students (name,age) values (%s,%s); ", [("hangyang",18),("12345",20)])
#执行select语句
cursor.execute("select * from students;")
#获取查询结果的第一条数据,返回的是一个元组
row_1 = cursor.fetchone()
# 获取前n行数据
row_2 = cursor.fetchmany(3)
# 获取所有数据
row_3 = cursor.fetchall()
# 提交,不然无法保存新建或者修改的数据
conn.commit()
# 获取最新自增ID
new_id = cursor.lastrowid
print(new_id)
# 关闭游标
cursor.close()
# 关闭连接
conn.close()上面的操作,获取到的返回结果都是元组,如果想获取到的结果是一个字典类型的话,可以使用下面这样的操作
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()

cursor = coon.cursor(cursor=pymysql.cursors.DictCursor)#需要指定游标的类型,字典类型
# 执行SQL
cursor.execute("select * from user;")
#获取返回结果,这个时候返回结果是一个字典
res = cursor.fetchone()#返回一条数据,如果结果是多条的话
print(res)
res2 = cursor.fetchall()#所有的数据一起返回

二、操作redis

redis是一个nosql类型的数据库,数据都存在内存中,有很快的读写速度,python操作redis使用redis模块,pip安装即可
import redis
r = redis.Redis(host='127.0.0.1',port=6379,db=0)#指定连接redis的端口和ip以及哪个数据库
r.set('name', 'value')#set string类型的值
r.setnx('name2', 'value')#设置的name的值,如果name不存在的时候才会设置
r.setex('name3', 'value', 3)#设置的name的值,和超时时间,过了时间key就会自动失效
r.mset(k1='v1',k2='v2')#批量设置值
r.get('name')#获取值
print(r.mget('k1','k2'))#批量获取key

r.delete('name')#删除值
r.delete('k1','k2')#批量删除
#======下面是操作哈希类型的
r.hset('hname', 'key', 'value')#set 哈希类型的值
r.hset('hname', 'key1', 'value2')#set 哈希类型的值
r.hsetnx('hname','key2','value23')#给name为hname设置key和value,和上面的不同的是key不存在的时候
#才会set
r.hmset('hname',{'k1':'v1','k2':'v2'})#批量设置哈希类型的key和value
r.hget('name', 'key')#获取哈希类型的值
print(r.hgetall('hname'))#获取这个name里所有的key和value
r.hdel('hname','key')#删除哈希类型的name里面指定的值
print(r.keys())#获取所有的key

三、操作mongodb

mongodb和redis一样,也是一个nosql类型的数据库,它和redis的区别是,redis把整个数据都放在内存,而mongodb是把数据放在磁盘上的。 python操作mongodb使用pymongo模块,pip安装即可,操作如下:
import pymongo
conn = pymongo.MongoClient(host='211.149.218.16',port=27017)#连接mongodb
db = conn.szz#选择哪个数据库
db.authenticate('admin','123456')#如果有账号密码的话,指定账号密码
collection = db.stus#使用数据库里面哪个集合,就相当于mysql里面的表
collection.drop()#删除指定的集合,也就是删除这个表
stu={
'name':'牛牛',
'age':38,
'sex':'男'
}
stus = [
{'name':'python',
'addr':'北京',
'sex':'未知',
'age':38
},
{
'name':'mongodb',
'addr':'USA',
'money':18.01,
'age':20
}
]
collection.save(stu)#插入单条数据
collection.insert(stus)#插入单条和多条,如果是多条的话,传入的就是一个list
=====比较操作符=======
# $lt
# 小于
# $lte
# 小于等于
# $gt
# 大于
# $gte
# 大于等于
# $ne
# 不等于
$set 获取前面的结果集
collection.update({'name':'牛牛'},{'name':'niuhy','age':20})#更新数据
collection.update({'name':'牛牛'},{'$set':{'addr':'河南'}})#在原来数据的基础上修改
collection.update({'name':'牛牛'},
{'$set':{'addr':'河南'}},
multi=True)#multi参数的作用是如果有多个结果的话,是否全部修改

collection.remove({'name':'牛牛'})#删除指定的数据,如果不传入参数,删除的是全部的数据
collection.remove()#删除全部数据
data = collection.find({'name':'mongodb'})#查询指定的数据
all_data = collection.find()#不写参数就是查询所有的数据
my_data = collection.find({'age':{'$gte':18}})#查询大于18岁的
for d in my_data:#获取数据,所有查询数据都需要使用循环来获取
print(d)#每个元素都是一个字典分享转载原文:牛牛杂货铺。 查看全部
我们在写代码的时候,经常会操作数据库,增删改查,数据库有很多类型,关系型数据库和非关系数据库,这里咱们介绍一下python怎么操作mysql、redis和mongodb。
 


、操作mysql


python3中操作mysql数据需要安装一个第三方模块,pymysql,使用pip install pymysql安装即可,在python2中是MySQLdb模块,在python3中没有MySQLdb模块了,所以使用pymysql。
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()
# 执行SQL,并返回收影响行数
effect_row = cursor.execute("update students set name = 'niuhy' where id = 1;")
# 执行SQL,并返回受影响行数
#effect_row = cursor.execute("update students set name = 'niuhy' where id = %s;", (1,))
# 执行SQL,并返回受影响行数
effect_row = cursor.executemany("insert into students (name,age) values (%s,%s); ", [("hangyang",18),("12345",20)])
#执行select语句
cursor.execute("select * from students;")
#获取查询结果的第一条数据,返回的是一个元组
row_1 = cursor.fetchone()
# 获取前n行数据
row_2 = cursor.fetchmany(3)
# 获取所有数据
row_3 = cursor.fetchall()
# 提交,不然无法保存新建或者修改的数据
conn.commit()
# 获取最新自增ID
new_id = cursor.lastrowid
print(new_id)
# 关闭游标
cursor.close()
# 关闭连接
conn.close()
上面的操作,获取到的返回结果都是元组,如果想获取到的结果是一个字典类型的话,可以使用下面这样的操作
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()

cursor = coon.cursor(cursor=pymysql.cursors.DictCursor)#需要指定游标的类型,字典类型
# 执行SQL
cursor.execute("select * from user;")
#获取返回结果,这个时候返回结果是一个字典
res = cursor.fetchone()#返回一条数据,如果结果是多条的话
print(res)
res2 = cursor.fetchall()#所有的数据一起返回


、操作redis


redis是一个nosql类型的数据库,数据都存在内存中,有很快的读写速度,python操作redis使用redis模块,pip安装即可
import redis
r = redis.Redis(host='127.0.0.1',port=6379,db=0)#指定连接redis的端口和ip以及哪个数据库
r.set('name', 'value')#set string类型的值
r.setnx('name2', 'value')#设置的name的值,如果name不存在的时候才会设置
r.setex('name3', 'value', 3)#设置的name的值,和超时时间,过了时间key就会自动失效
r.mset(k1='v1',k2='v2')#批量设置值
r.get('name')#获取值
print(r.mget('k1','k2'))#批量获取key

r.delete('name')#删除值
r.delete('k1','k2')#批量删除
#======下面是操作哈希类型的
r.hset('hname', 'key', 'value')#set 哈希类型的值
r.hset('hname', 'key1', 'value2')#set 哈希类型的值
r.hsetnx('hname','key2','value23')#给name为hname设置key和value,和上面的不同的是key不存在的时候
#才会set
r.hmset('hname',{'k1':'v1','k2':'v2'})#批量设置哈希类型的key和value
r.hget('name', 'key')#获取哈希类型的值
print(r.hgetall('hname'))#获取这个name里所有的key和value
r.hdel('hname','key')#删除哈希类型的name里面指定的值
print(r.keys())#获取所有的key


、操作mongodb


mongodb和redis一样,也是一个nosql类型的数据库,它和redis的区别是,redis把整个数据都放在内存,而mongodb是把数据放在磁盘上的。 python操作mongodb使用pymongo模块,pip安装即可,操作如下:
import pymongo
conn = pymongo.MongoClient(host='211.149.218.16',port=27017)#连接mongodb
db = conn.szz#选择哪个数据库
db.authenticate('admin','123456')#如果有账号密码的话,指定账号密码
collection = db.stus#使用数据库里面哪个集合,就相当于mysql里面的表
collection.drop()#删除指定的集合,也就是删除这个表
stu={
'name':'牛牛',
'age':38,
'sex':'男'
}
stus = [
{'name':'python',
'addr':'北京',
'sex':'未知',
'age':38
},
{
'name':'mongodb',
'addr':'USA',
'money':18.01,
'age':20
}
]
collection.save(stu)#插入单条数据
collection.insert(stus)#插入单条和多条,如果是多条的话,传入的就是一个list
=====比较操作符=======
# $lt
# 小于
# $lte
# 小于等于
# $gt
# 大于
# $gte
# 大于等于
# $ne
# 不等于
$set 获取前面的结果集
collection.update({'name':'牛牛'},{'name':'niuhy','age':20})#更新数据
collection.update({'name':'牛牛'},{'$set':{'addr':'河南'}})#在原来数据的基础上修改
collection.update({'name':'牛牛'},
{'$set':{'addr':'河南'}},
multi=True)#multi参数的作用是如果有多个结果的话,是否全部修改

collection.remove({'name':'牛牛'})#删除指定的数据,如果不传入参数,删除的是全部的数据
collection.remove()#删除全部数据
data = collection.find({'name':'mongodb'})#查询指定的数据
all_data = collection.find()#不写参数就是查询所有的数据
my_data = collection.find({'age':{'$gte':18}})#查询大于18岁的
for d in my_data:#获取数据,所有查询数据都需要使用循环来获取
print(d)#每个元素都是一个字典
分享转载原文:牛牛杂货铺

File "collect_info.py", line 109, in <module>

编程语言采菊篱下 回复了问题 • 2 人关注 • 3 个回复 • 1085 次浏览 • 2017-04-19 13:58 • 来自相关话题

Python字符串反转方法小记

编程语言采菊篱下 发表了文章 • 1 个评论 • 375 次浏览 • 2017-04-09 15:29 • 来自相关话题

有个朋友开突然问我在Python下怎么把字符串倒过来排序,刚开始我懵逼了,倒过来排序有什么意义,你的场景是什么,如果你单纯问我这个作为一个小考验,我觉得搜索一大推,自行Google就好啊。他说他们需要针对密码加密,简单的逻辑就是反转加密实现,厉害了疙瘩。下面我主要记录一下Python下的几种方法。

No.1 切片方式

字符串的切片跟列表是一样的,主要是利用切片的扩展语法-1来实现def rev1(cont):
return cont[::-1]
切片详细语法查看:https://docs.python.org/2/whatsnew/2.3.html#extended-slices 

No.2 列表reverse实现

利用列表的reverse()方法这个特性,可以先将字符串转换成列表,利用reverse()方法进行反转后,再处理成字符串。def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)

No.3 内置函数reversed实现

def rev3(cont):
return ''.join(reversed(cont))

No.4 递归方法

def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]# 在Python 3里,reduce()内置函数已经被从全局名字空间里移除了,它现在被放置在fucntools模块里
from functools import reduce

def rev5(cont):
return reduce(lambda x, y : y + x, cont)

No.5 字符串拼接

def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_stringdef rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)
如上几种方法效率比较:#!/usr/bin/env python3
# Author: nock
from functools import reduce
import timeit

cont = 'kcon' * 20

def rev1(cont):
return cont[::-1]

def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)

def rev3(cont):
return ''.join(reversed(cont))

def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]

def rev5(cont):
return reduce(lambda x, y : y + x, cont)

def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_string

def rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)

if __name__ == '__main__':
print("rev1 run time is: %s" % min(timeit.repeat(lambda: rev1(cont))))
print("rev2 run time is: %s" % min(timeit.repeat(lambda: rev2(cont))))
print("rev3 run time is: %s" % min(timeit.repeat(lambda: rev3(cont))))
print("rev4 run time is: %s" % min(timeit.repeat(lambda: rev4(cont))))
print("rev5 run time is: %s" % min(timeit.repeat(lambda: rev5(cont))))
print("rev6 run time is: %s" % min(timeit.repeat(lambda: rev6(cont))))
print("rev7 run time is: %s" % min(timeit.repeat(lambda: rev7(cont))))时间结果如下:rev1 run time is: 0.45436444599181414
rev2 run time is: 2.3974227079888806
rev3 run time is: 2.633627591014374
rev4 run time is: 3.0160443240310997
rev5 run time is: 16.342944753996562
rev6 run time is: 12.666344199969899
rev7 run time is: 14.762871471000835所以如上可以看出,还是用切片的方法最好,所以记住切片步长为-1就可反转就好。 查看全部
有个朋友开突然问我在Python下怎么把字符串倒过来排序,刚开始我懵逼了,倒过来排序有什么意义,你的场景是什么,如果你单纯问我这个作为一个小考验,我觉得搜索一大推,自行Google就好啊。他说他们需要针对密码加密,简单的逻辑就是反转加密实现,厉害了疙瘩。下面我主要记录一下Python下的几种方法。


No.1 切片方式


字符串的切片跟列表是一样的,主要是利用切片的扩展语法-1来实现
def rev1(cont):
return cont[::-1]
切片详细语法查看:https://docs.python.org/2/whatsnew/2.3.html#extended-slices 


No.2 列表reverse实现


利用列表的reverse()方法这个特性,可以先将字符串转换成列表,利用reverse()方法进行反转后,再处理成字符串。
def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)


No.3 内置函数reversed实现


def rev3(cont):
return ''.join(reversed(cont))


No.4 递归方法


def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]
# 在Python 3里,reduce()内置函数已经被从全局名字空间里移除了,它现在被放置在fucntools模块里
from functools import reduce

def rev5(cont):
return reduce(lambda x, y : y + x, cont)


No.5 字符串拼接


def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_string
def rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)

如上几种方法效率比较:
#!/usr/bin/env python3
# Author: nock
from functools import reduce
import timeit

cont = 'kcon' * 20

def rev1(cont):
return cont[::-1]

def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)

def rev3(cont):
return ''.join(reversed(cont))

def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]

def rev5(cont):
return reduce(lambda x, y : y + x, cont)

def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_string

def rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)

if __name__ == '__main__':
print("rev1 run time is: %s" % min(timeit.repeat(lambda: rev1(cont))))
print("rev2 run time is: %s" % min(timeit.repeat(lambda: rev2(cont))))
print("rev3 run time is: %s" % min(timeit.repeat(lambda: rev3(cont))))
print("rev4 run time is: %s" % min(timeit.repeat(lambda: rev4(cont))))
print("rev5 run time is: %s" % min(timeit.repeat(lambda: rev5(cont))))
print("rev6 run time is: %s" % min(timeit.repeat(lambda: rev6(cont))))
print("rev7 run time is: %s" % min(timeit.repeat(lambda: rev7(cont))))
时间结果如下:
rev1 run time is: 0.45436444599181414
rev2 run time is: 2.3974227079888806
rev3 run time is: 2.633627591014374
rev4 run time is: 3.0160443240310997
rev5 run time is: 16.342944753996562
rev6 run time is: 12.666344199969899
rev7 run time is: 14.762871471000835
所以如上可以看出,还是用切片的方法最好,所以记住切片步长为-1就可反转就好。

Python生成器解析式和Zip函数介绍

编程语言采菊篱下 发表了文章 • 0 个评论 • 342 次浏览 • 2017-03-23 17:31 • 来自相关话题

生成器解析式

对列表解析来说,只需要简单的把中括号换成小括号就可以了,生成器解析式是按需计算的或者说延迟计算的或者叫惰性求值。
 
#!/usr/bin/env python3
# Author: nock

def inc(x):
print('inc {0}'.format(x))
return x + 1

# 生成一个迭代器对象
obj = (inc(x) for x in range(10))
print(obj)

Result:
<generator object <genexpr> at 0x107d87678>#!/usr/bin/env python3
# Author: nock

# 生成一个迭代器对象
obj = (x for x in range(10))
l = [x for x in range(10)]

print(next(obj))
print(next(obj))
print(next(obj))

print(l[4])
try:
print(obj[1])
except Exception as e:
print("Exception is: {0}".format(e))
print(next(obj))Result:
0
1
2
4
Exception is: 'generator' object is not subscriptable
3生成器无下标获取。
 

Zip





zip 函数用于合并多个可迭代对象,合并后的长度等于最短的可迭代对象的长度 查看全部


生成器解析式


对列表解析来说,只需要简单的把中括号换成小括号就可以了,生成器解析式是按需计算的或者说延迟计算的或者叫惰性求值。
 
#!/usr/bin/env python3
# Author: nock

def inc(x):
print('inc {0}'.format(x))
return x + 1

# 生成一个迭代器对象
obj = (inc(x) for x in range(10))
print(obj)

Result:
<generator object <genexpr> at 0x107d87678>
#!/usr/bin/env python3
# Author: nock

# 生成一个迭代器对象
obj = (x for x in range(10))
l = [x for x in range(10)]

print(next(obj))
print(next(obj))
print(next(obj))

print(l[4])
try:
print(obj[1])
except Exception as e:
print("Exception is: {0}".format(e))
print(next(obj))
Result:
0
1
2
4
Exception is: 'generator' object is not subscriptable
3
生成器无下标获取。
 


Zip


zip.png

zip 函数用于合并多个可迭代对象,合并后的长度等于最短的可迭代对象的长度

解锁Python集合推导式和字典推导式

编程语言采菊篱下 发表了文章 • 0 个评论 • 416 次浏览 • 2017-03-19 22:23 • 来自相关话题

集合推导式

集合推导式(set comprehensions)跟列表推导式也是类似的, 唯一的区别在于它们使用大括号{}表示。Code:
sets = {x for x in range(10)}
Result:
{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}



集合解析把列表解析中的中括号变成大括号,返回集合。
 
下面我们来个应用场景,一直一个列表中有很多元素,我们做到快速去重。Code:
heavy = {x for x in [2, 3, 5, 3, 5, 2, 6]}
print(heavy)
Result:
{2, 3, 5, 6}集合推导式生成内容,结果要是可hash的:





字典推导式

字典推导式(dict comprehensions)和列表推导的使用方法也是类似的。




字典解析也是使用大括号包围,并且需要两个表达式,一个生成key, 一个生成value 两个表达式之间使用冒号分割,返回结果是字典.

说了这么多推导式,为什么没有元组推导式呢,元组和列表的操作几乎是一样的,除了不可变特性以外Code:
tuple([x for x in range(10)])
Result:
(0, 1, 2, 3, 4, 5, 6, 7, 8, 9) 查看全部


集合推导式


集合推导式(set comprehensions)跟列表推导式也是类似的, 唯一的区别在于它们使用大括号{}表示。
Code:
sets = {x for x in range(10)}
Result:
{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}
type.png

集合解析把列表解析中的中括号变成大括号,返回集合。
 
下面我们来个应用场景,一直一个列表中有很多元素,我们做到快速去重。
Code:
heavy = {x for x in [2, 3, 5, 3, 5, 2, 6]}
print(heavy)
Result:
{2, 3, 5, 6}
集合推导式生成内容,结果要是可hash的:
hashable.png


字典推导式


字典推导式(dict comprehensions)和列表推导的使用方法也是类似的。
dictreb.png

字典解析也是使用大括号包围,并且需要两个表达式,一个生成key, 一个生成value 两个表达式之间使用冒号分割,返回结果是字典.

说了这么多推导式,为什么没有元组推导式呢,元组和列表的操作几乎是一样的,除了不可变特性以外
Code:
tuple([x for x in range(10)])
Result:
(0, 1, 2, 3, 4, 5, 6, 7, 8, 9)

Python使用类来写装饰器

编程语言采菊篱下 发表了文章 • 0 个评论 • 306 次浏览 • 2017-03-19 17:37 • 来自相关话题

前两天发现了装饰器可以直接使用类来写,分享一下,需要用类里面的__call__方法,__call__方法就是可以把这个实例当成一个函数来调用,如果正常使用类里面的方法的话,实例方法要先实例化类,然后才能调用,静态方法、类方法则需要用类名或者实例化之后的对象来调用,而实例化之后的这个对象,是不能被调用的,__call__方法就是把这个实例变成一个可以调用的对象,也就是说实例化之后,这个对象就可以和一个普通函数一样被调用。

示例代码如下:
class Foo:
def __call__(self, *args, **kwargs):
print('call....')
def test(self):#
print('test....')
if __name__ == '__main__':
t = Foo()#实例化类
t.test()#正常调用实例方法
t()#直接调用实例化之后的对象运行结果:
>>>test.... #这个是调用test方法的时候输出的
>>>call....#这个是执行调用这个实例化之后的方法输出的理解了上面的之后,就可以使用class来写一个装饰器了,计算程序的运行时间,当然思想和以前用函数写装饰器是一样的
class Fuck(object):
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
import time
start_time = time.time()
res = self.func(*args, **kwargs)
end_time = time.time()
print('the function "%s" run time is %s' % (self.func.__name__,
(end_time - start_time)))
return res
@Fuck
def run(name):
import time
time.sleep(1)
return 'sb_%s' % name
print(run('hyf'))运行结果:
>>>the function "run" run time is 1.0001001358032227#这个是装饰器帮我们计算的函数运行时间
>>>sb_hyf#这个是正常运行run函数的时候,返回的值
原文地址:http://www.nnzhp.cn/blog/2017/01/16/1/  查看全部
前两天发现了装饰器可以直接使用类来写,分享一下,需要用类里面的__call__方法,__call__方法就是可以把这个实例当成一个函数来调用,如果正常使用类里面的方法的话,实例方法要先实例化类,然后才能调用,静态方法、类方法则需要用类名或者实例化之后的对象来调用,而实例化之后的这个对象,是不能被调用的,__call__方法就是把这个实例变成一个可以调用的对象,也就是说实例化之后,这个对象就可以和一个普通函数一样被调用。

示例代码如下:
class Foo:
def __call__(self, *args, **kwargs):
print('call....')
def test(self):#
print('test....')
if __name__ == '__main__':
t = Foo()#实例化类
t.test()#正常调用实例方法
t()#直接调用实例化之后的对象
运行结果:
>>>test.... #这个是调用test方法的时候输出的
>>>call....#这个是执行调用这个实例化之后的方法输出的
理解了上面的之后,就可以使用class来写一个装饰器了,计算程序的运行时间,当然思想和以前用函数写装饰器是一样的
class Fuck(object):
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
import time
start_time = time.time()
res = self.func(*args, **kwargs)
end_time = time.time()
print('the function "%s" run time is %s' % (self.func.__name__,
(end_time - start_time)))
return res
@Fuck
def run(name):
import time
time.sleep(1)
return 'sb_%s' % name
print(run('hyf'))
运行结果:
>>>the function "run" run time is 1.0001001358032227#这个是装饰器帮我们计算的函数运行时间
>>>sb_hyf#这个是正常运行run函数的时候,返回的值
原文地址:http://www.nnzhp.cn/blog/2017/01/16/1/ 

解锁Python列表推导式

编程语言采菊篱下 发表了文章 • 0 个评论 • 347 次浏览 • 2017-03-18 00:28 • 来自相关话题

Pythonic的核心就是Python之禅,而Python的列表推导式就得以很好的体现。

列表推导式

定义:
列表推导式(又称列表解析式)提供了一种简明扼要的方法来创建列表。

它的结构是在一个中括号里包含一个表达式,然后是一个for语句,然后是0个或多个for或者if语句。那个表达式可以是任意的,意思是你可以在列表中放入任意类型的对象。返回结果将是一个新的列表,在这个以if和for语句为上下文的表达式运行完成之后产生。
 
列表解析的一般形式:
[expr for item in itratorable]
Code: [2 ** n for n in range(10)]

Result: [1, 2, 4, 8, 16, 32, 64, 128, 256, 512]



列表解析返回的是列表, 列表的内容是表达式执行的结果.
 
[expr for item in iterable if cond]

[x ** 0.5 for x in range(10) if x % 2 == 0]
[0.0, 1.4142135623730951, 2.0, 2.449489742783178, 2.8284271247461903][expr for item in iterable if cond1 if cond2]

[x for x in range(10) if x % 2 == 0 if x > 1]
[2, 4, 6, 8][expr for item1 in iterable1 for item2 in iterable2]

[(x, y) for x in range(10) for y in range(10) if (x+y) %2 == 0]







列表解析用于对可迭代对象做过滤和转换,返回值是列表.
 
特性一:代码变短,可读性更好




从上图代码示例中我们明显可以看出,列表推导式相比常规方法,写出来的代码更加符合pythonic,更加简短,可读性更好。
 
有些人甚至更喜欢使用它而不是filter函数生成列表,但是当你使用列表推导式效果会更加,列表推导式在有些情况下超赞,特别是当你需要使用for循环来生成一个新列表.
 
特征二:推导式速度更快
#!/usr/bin/env python3
# author: nock
import timeit

lst = list(range(10))
# 常规方法
def origin(lst):
plus_one = []
for i in lst:
plus_one.append(i + 1)
return plus_one

# 列表推导式
def fast(lst):
return [ x + 1 for x in lst ]

otime = timeit.timeit('origin(range(10))', globals=globals())
print("func origin exec time is {0}".format(otime))

ftime = timeit.timeit('fast(range(10))', globals=globals())
print("func origin exec time is {0}".format(ftime))结果:
func origin exec time is 2.1059355960023822
func origin exec time is 1.6507169340038672
如果你使用map或者filter结合lambda生成列表,也是没有列表推导式速度快的,有兴趣的可以自己Coding一下。
  查看全部
Pythonic的核心就是Python之禅,而Python的列表推导式就得以很好的体现。


列表推导式


定义:
列表推导式(又称列表解析式)提供了一种简明扼要的方法来创建列表。

它的结构是在一个中括号里包含一个表达式,然后是一个for语句,然后是0个或多个for或者if语句。那个表达式可以是任意的,意思是你可以在列表中放入任意类型的对象。返回结果将是一个新的列表,在这个以if和for语句为上下文的表达式运行完成之后产生。
 
列表解析的一般形式:
[expr for item in itratorable]

Code: [2 ** n for n in range(10)]

Result: [1, 2, 4, 8, 16, 32, 64, 128, 256, 512]
listresult.png

列表解析返回的是列表, 列表的内容是表达式执行的结果.
 
[expr for item in iterable if cond]

[x ** 0.5 for x in range(10) if x % 2 == 0]
[0.0, 1.4142135623730951, 2.0, 2.449489742783178, 2.8284271247461903]
[expr for item in iterable if cond1 if cond2]

[x for x in range(10) if x % 2 == 0 if x > 1]
[2, 4, 6, 8]
[expr for item1 in iterable1 for item2 in iterable2]

[(x, y) for x in range(10) for y in range(10) if (x+y) %2 == 0]
listerror.png

listdie.png

列表解析用于对可迭代对象做过滤和转换,返回值是列表.
 
特性一:代码变短,可读性更好
list.png

从上图代码示例中我们明显可以看出,列表推导式相比常规方法,写出来的代码更加符合pythonic,更加简短,可读性更好。
 
有些人甚至更喜欢使用它而不是filter函数生成列表,但是当你使用列表推导式效果会更加,列表推导式在有些情况下超赞,特别是当你需要使用for循环来生成一个新列表.
 
特征二:推导式速度更快
#!/usr/bin/env python3
# author: nock
import timeit

lst = list(range(10))
# 常规方法
def origin(lst):
plus_one = []
for i in lst:
plus_one.append(i + 1)
return plus_one

# 列表推导式
def fast(lst):
return [ x + 1 for x in lst ]

otime = timeit.timeit('origin(range(10))', globals=globals())
print("func origin exec time is {0}".format(otime))

ftime = timeit.timeit('fast(range(10))', globals=globals())
print("func origin exec time is {0}".format(ftime))
结果:
func origin exec time is 2.1059355960023822
func origin exec time is 1.6507169340038672

如果你使用map或者filter结合lambda生成列表,也是没有列表推导式速度快的,有兴趣的可以自己Coding一下。
 

老男孩Python开发2016最新14期前10周视频【限免】

编程语言Target 回复了问题 • 5 人关注 • 4 个回复 • 2950 次浏览 • 2017-01-07 22:33 • 来自相关话题

条新动态, 点击查看
luotianshuai

luotianshuai 回答了问题 • 2015-12-14 12:59 • 3 个回复 不感兴趣

Python在生产环境都可以用来做什么?

赞同来自:

<Python能做什么Web程序

Python经常被用于Web开发。比如,通过mod_wsgi模块,Apache可以运行用Python编写的Web程序。使用Python语言 编写的Gunicorn作为Web服务器,也能够运行Python语言编写的Web... 显示全部 »
<Python能做什么Web程序

Python经常被用于Web开发。比如,通过mod_wsgi模块,Apache可以运行用Python编写的Web程序。使用Python语言 编写的Gunicorn作为Web服务器,也能够运行Python语言编写的Web程序。Python定义了WSGI标准应用接口来协调Http服务器与 基于Python的Web程序之间的沟通。一些Web框架,如Django、Pyramid、TurboGears、Tornado、web2py、 Zope、Flask等,可以让程序员轻松地开发和管理复杂的Web程序。

Python对于各种网络协议的支持很完善,因此经常被用于编写服务器软件、网络蠕虫。第三方库Twisted支持异步在线编写程序和多数标准的网 络协议(包含客户端和服务器),并且提供了多种工具,被广泛用于编写高性能的服务器软件。另有gevent这个流行的第三方库,同样能够支持高性能高并发 的网络开发。

GUI开发

Python本身包含的Tkinter库能够支持简单的GUI开发。但是越来越多的Python程序员选择wxPython或者PyQt等GUI包 来开发跨平台的桌面软件。使用它们开发的桌面软件运行速度快,与用户的桌面环境相契合。通过PyInstaller还能将程序发布为独立的安装程序包。

操作系统

在很多操作系统里,Python是标准的系统组件。大多数Linux发布版以及NetBSD、OpenBSD和Mac OS X都集成了Python,可以在终端机下直接运行Python。有一些Linux发布版的安装器使用Python语言编写,比如Ubuntu的 Ubiquity安装器、Red Hat Linux和Fedora的Anaconda安装器。Gentoo Linux使用Python来编写它的Portage包管理系统。Python标准库包含了多个调用作业系统功能的库。通过pywin32这个第三方软件 包,Python能够访问Windows的COM服务及其它Windows API。使用IronPython,Python程序能够直接调用.Net Framework。

其他

NumPy、SciPy、Matplotlib可以让Python程序员编写科学计算程序。有些公司会使用Scons代替make构建C 程序。

很多游戏使用C 编写图形显示等高性能模块,而使用Python或者Lua编写游戏的逻辑、服务器。相较于Python,Lua的功能更简单、体 积更小;而Python则支持更多的特性和数据类型。很多游戏,如EVE Online使用Python来处理游戏中繁多的逻辑。

YouTube、Google、Yahoo!、NASA都在内部大量地使用Python。OLPC的作业系统Sugar项目的大多数软件都是使用Python编写

 
所以他的应用范围大概分为:

数据分析
系统编程
组件集成
网络服务
图像处理
数值计算和科学计算>

以上是python能做的非常丰富!
采菊篱下

采菊篱下 回答了问题 • 2015-12-22 19:00 • 2 个回复 不感兴趣

Python的web框架有哪些

赞同来自:

Django 
Flask  
Pyramid
Tornado
Bottle
web.py
web2.py
更多信息查看:http://www.csdn.net/article/2013-08-08/2816494-6-pillars-of-python-as... 显示全部 »
Django 
Flask  
Pyramid
Tornado
Bottle
web.py
web2.py
更多信息查看:http://www.csdn.net/article/2013-08-08/2816494-6-pillars-of-python-assessment-of-best-python-web-frameworks
http://python.jobbole.com/72306/?replytocom=57112
 
fhand = urllib.request.urlopen('http://www.pythonlearn.com/code/mbox.txt').readlines()

for line in fhand:
# ...orfhand = urllib... 显示全部 »
fhand = urllib.request.urlopen('http://www.pythonlearn.com/code/mbox.txt').readlines()

for line in fhand:
# ...orfhand = urllib.request.urlopen('http://www.pythonlearn.com/code/mbox.txt').read().decode()

for line in fhand.split('\n'):
# ...
采菊篱下

采菊篱下 回答了问题 • 2016-12-27 11:38 • 2 个回复 不感兴趣

python FTP问题

赞同来自:

@Ansible 说的对,是你代码有问题,ftp这个对象不对。正常代码如下:
# 例:FTP编程
from ftplib import FTP

ftp = FTP()
timeout = 30
port = 21
ftp.c... 显示全部 »
@Ansible 说的对,是你代码有问题,ftp这个对象不对。正常代码如下:
# 例:FTP编程
from ftplib import FTP

ftp = FTP()
timeout = 30
port = 21
ftp.connect('192.168.1.188',port,timeout) # 连接FTP服务器
ftp.login('UserName','888888') # 登录
print ftp.getwelcome() # 获得欢迎信息
ftp.cwd('file/test') # 设置FTP路径
list = ftp.nlst() # 获得目录列表
for name in list:
print(name) # 打印文件名字
path = 'd:/data/' + name # 文件保存路径
f = open(path,'wb') # 打开要保存文件
filename = 'RETR ' + name # 保存FTP文件
ftp.retrbinary(filename,f.write) # 保存FTP上的文件
ftp.delete(name) # 删除FTP文件
ftp.storbinary('STOR '+filename, open(path, 'rb')) # 上传FTP文件
ftp.quit() # 退出FTP服务器 从上面代码你可以看出ftp.retrbinary()  这个方法ftp对象是------> ftp = FTP(),  而不是你代码里面的---->ftp = ftpconnect()
 
完整的参考模板:
#!/usr/bin/python
# -*- coding: utf-8 -*-
import ftplib
import os
import socket

HOST = 'ftp.mozilla.org'
DIRN = 'pub/mozilla.org/webtools'
FILE = 'bugzilla-3.6.7.tar.gz'
def main():
try:
f = ftplib.FTP(HOST)
except (socket.error, socket.gaierror):
print 'ERROR:cannot reach " %s"' % HOST
return
print '***Connected to host "%s"' % HOST

try:
f.login()
except ftplib.error_perm:
print 'ERROR: cannot login anonymously'
f.quit()
return
print '*** Logged in as "anonymously"'
try:
f.cwd(DIRN)
except ftplib.error_perm:
print 'ERRORL cannot CD to "%s"' % DIRN
f.quit()
return
print '*** Changed to "%s" folder' % DIRN
try:
#传一个回调函数给retrbinary() 它在每接收一个二进制数据时都会被调用
f.retrbinary('RETR %s' % FILE, open(FILE, 'wb').write)
except ftplib.error_perm:
print 'ERROR: cannot read file "%s"' % FILE
os.unlink(FILE)
else:
print '*** Downloaded "%s" to CWD' % FILE
f.quit()
return

if __name__ == '__main__':
main()

图解Python 集合

编程语言采菊篱下 发表了文章 • 2 个评论 • 765 次浏览 • 2016-08-10 23:41 • 来自相关话题

集合基本功能

集合是一个无序的,不重复的数据组合,用{}表示,它的主要作用如下:
去重,把一个列表变成集合,就会自动去重关系测试,测试两组数据之前的交集、差集、并集、子集等关系
 集合创建:
>>> set_job = set(['DEV', 'OPS', 'DBA', 'QA', 'Sales'])
>>> set_man = set(('lucky', 'jack', 'andy', 'tom', 'andy', 'jim'))
>>> print(set_job, type(set_job))
{'DEV', 'OPS', 'Sales', 'QA', 'DBA'} <class 'set'>
>>> print(set_man, type(set_man)) # 天生去重,只有一个andy了
{'andy', 'jack', 'lucky', 'tom', 'jim'} <class 'set'>
 
元素添加:
>>> set_job = set(['DEV', 'OPS', 'DBA', 'QA', 'Sales'])
>>> set_job.add('HR') # add方法只能添加一个
>>> print(set_job)
{'QA', 'HR', 'Sales', 'DEV', 'OPS', 'DBA'}
>>> set_job.update(['FD', 'MD', 'MD'])
>>> print(set_job)
{'QA', 'HR', 'Sales', 'DEV', 'MD', 'OPS', 'FD', 'DBA'}
>>> set_job.update(('AD', 'PD')) # update方法可以添加是列表或者元组,去重,如果添加的为一个单独字符串,则把字符串拆成字母添加到集合中
>>> print(set_job)
{'QA', 'HR', 'PD', 'Sales', 'DEV', 'MD', 'OPS', 'AD', 'FD', 'DBA'}
元素删除:
>>> set_job = {'QA', 'HR', 'PD', 'Sales', 'DEV', 'MD', 'OPS', 'AD', 'FD', 'DBA'}
>>> set_job.remove('PD') # 删除指定元素
>>> set_job.remove('xx') # 元素不存在则报错 KeyError
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'xx'
>>> print(set_job)
{'QA', 'HR', 'MD', 'DEV', 'Sales', 'OPS', 'AD', 'FD', 'DBA'}
>>> set_job.pop() # 随机删除一个元素
'QA'
>>> print(set_job)
{'HR', 'MD', 'DEV', 'Sales', 'OPS', 'AD', 'FD', 'DBA'}
>>> set_job.discard('OPS') # 指定删除
>>> set_job.discard('xxx') # 不存在返回None,不会报KeyError
>>> print(set_job)
{'HR', 'MD', 'DEV', 'Sales', 'AD', 'FD', 'DBA'}
其他:
>>> set_job = {'QA', 'HR', 'PD', 'Sales', 'DEV', 'MD', 'OPS', 'AD', 'FD', 'DBA'}
>>> len(set_job)  # 集合长度
10
>>> 'QA' in set_job  # 判断是否在集合中
True
>>> 'XXX' not in set_job # 不在集合中
True
>>> for i in set_job:   # 循环
...     print(i)

集合关系测试

交集:



>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> print(set_a.intersection(set_b)) # 常规方式
{5, 6}
>>> print(set_a & set_b) # 运算符(&)方式
{5, 6}
并集



>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = set_a.union(set_b)    # 关键字union做并集运算 先后顺序无关,谁并谁都可以
>>> print(set_c)
{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}
>>> 
>>> set_c = set_a | set_b     # 运算符关键符 | 做并集运算  先后顺序无关,谁并谁都可以
>>> print(set_c)
{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}

差集



>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = set_a - set_b # a集合跟b集合做差集 关键符 -
>>> print(set_c)
{8, 9, 10, 7}
>>> set_d = set_b - set_a # b集合跟a集合做差集 关键符 -
>>> print(set_d)
{1, 2, 3, 4}
>>> set_c = set_a.difference(set_b) # a集合跟b集合做差集 关键字difference
>>> print(set_c)
{8, 9, 10, 7}
>>> set_d = set_b.difference(set_a) # b集合跟a集合做差集 关键字difference
>>> print(set_d)
{1, 2, 3, 4}
 
子集父集




拿苹果来打比方就是,把苹果掰开,然后掰开的一小部分就是子集,然后整个苹果就是父集
>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = {7, 8, 9, 10}
>>> set_d = {1, 2, 3, 4}
>>> set_e = {5, 6}
>>> set_f = {11, 12, 13, 14, 15, 16}
>>> set_c.issubset(set_a) # 测试集合c是否是集合a的子集 放回布尔值 关键字issubset
True
>>> set_d.issubset(set_b) # 测试集合d是否是集合b的子集 返回布尔值 issubset
True
>>> set_e.issubset(set_a)
True
>>> set_e.issubset(set_b)
True
>>> set_e <= set_a # 测试集合e是否是集合a的子集 关键符 <=
True
>>> set_e <= set_b
True
>>> set_f.issuperset(set_a) # 测试f集合是否是a集合的父集
False
>>> set_a.issuperset(set_e) # 测试a集合是否是集合e的父集 关键字issuperset
True
>>> set_b >= set_e # 测试集合b是否是集合e的父集 关键符 >=
True
>>> set_b >= set_d
True
对称差集
对称差集就是两个集合去掉相同的部分,然后剩下的所有元素组成的集合



>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = set_a.symmetric_difference(set_b) # 集合a和集合b做对称差集 关键字symmetric_difference
>>> print(set_c)
{1, 2, 3, 4, 7, 8, 9, 10}
>>> set_c = set_a ^ set_b # 集合a和集合b做对称差集 关键符 ^
>>> print(set_c)
{1, 2, 3, 4, 7, 8, 9, 10}
>>> set_c = set_b ^ set_a
>>> print(set_c)
{1, 2, 3, 4, 7, 8, 9, 10}
所有方法:
class set(object):
"""
set() -> new empty set object
set(iterable) -> new set object

Build an unordered collection of unique elements.
"""
def add(self, *args, **kwargs): # real signature unknown
"""
Add an element to a set.

This has no effect if the element is already present.
"""
pass

def clear(self, *args, **kwargs): # real signature unknown
""" Remove all elements from this set. """
pass

def copy(self, *args, **kwargs): # real signature unknown
""" Return a shallow copy of a set. """
pass

def difference(self, *args, **kwargs): # real signature unknown
"""
Return the difference of two or more sets as a new set.

(i.e. all elements that are in this set but not the others.)
"""
pass

def difference_update(self, *args, **kwargs): # real signature unknown
""" Remove all elements of another set from this set. """
pass

def discard(self, *args, **kwargs): # real signature unknown
"""
Remove an element from a set if it is a member.

If the element is not a member, do nothing.
"""
pass

def intersection(self, *args, **kwargs): # real signature unknown
"""
Return the intersection of two sets as a new set.

(i.e. all elements that are in both sets.)
"""
pass

def intersection_update(self, *args, **kwargs): # real signature unknown
""" Update a set with the intersection of itself and another. """
pass

def isdisjoint(self, *args, **kwargs): # real signature unknown
""" Return True if two sets have a null intersection. """
pass

def issubset(self, *args, **kwargs): # real signature unknown
""" Report whether another set contains this set. """
pass

def issuperset(self, *args, **kwargs): # real signature unknown
""" Report whether this set contains another set. """
pass

def pop(self, *args, **kwargs): # real signature unknown
"""
Remove and return an arbitrary set element.
Raises KeyError if the set is empty.
"""
pass

def remove(self, *args, **kwargs): # real signature unknown
"""
Remove an element from a set; it must be a member.

If the element is not a member, raise a KeyError.
"""
pass

def symmetric_difference(self, *args, **kwargs): # real signature unknown
"""
Return the symmetric difference of two sets as a new set.

(i.e. all elements that are in exactly one of the sets.)
"""
pass

def symmetric_difference_update(self, *args, **kwargs): # real signature unknown
""" Update a set with the symmetric difference of itself and another. """
pass

def union(self, *args, **kwargs): # real signature unknown
"""
Return the union of sets as a new set.

(i.e. all elements that are in either set.)
"""
pass

def update(self, *args, **kwargs): # real signature unknown
""" Update a set with the union of itself and others. """
pass 查看全部


集合基本功能


集合是一个无序的,不重复的数据组合,用{}表示,它的主要作用如下:
  1. 去重,把一个列表变成集合,就会自动去重
  2. 关系测试,测试两组数据之前的交集、差集、并集、子集等关系

 集合创建:
>>> set_job = set(['DEV', 'OPS', 'DBA', 'QA', 'Sales'])
>>> set_man = set(('lucky', 'jack', 'andy', 'tom', 'andy', 'jim'))
>>> print(set_job, type(set_job))
{'DEV', 'OPS', 'Sales', 'QA', 'DBA'} <class 'set'>
>>> print(set_man, type(set_man)) # 天生去重,只有一个andy了
{'andy', 'jack', 'lucky', 'tom', 'jim'} <class 'set'>

 
元素添加:
>>> set_job = set(['DEV', 'OPS', 'DBA', 'QA', 'Sales'])
>>> set_job.add('HR') # add方法只能添加一个
>>> print(set_job)
{'QA', 'HR', 'Sales', 'DEV', 'OPS', 'DBA'}
>>> set_job.update(['FD', 'MD', 'MD'])
>>> print(set_job)
{'QA', 'HR', 'Sales', 'DEV', 'MD', 'OPS', 'FD', 'DBA'}
>>> set_job.update(('AD', 'PD')) # update方法可以添加是列表或者元组,去重,如果添加的为一个单独字符串,则把字符串拆成字母添加到集合中
>>> print(set_job)
{'QA', 'HR', 'PD', 'Sales', 'DEV', 'MD', 'OPS', 'AD', 'FD', 'DBA'}

元素删除:
>>> set_job = {'QA', 'HR', 'PD', 'Sales', 'DEV', 'MD', 'OPS', 'AD', 'FD', 'DBA'}
>>> set_job.remove('PD') # 删除指定元素
>>> set_job.remove('xx') # 元素不存在则报错 KeyError
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'xx'
>>> print(set_job)
{'QA', 'HR', 'MD', 'DEV', 'Sales', 'OPS', 'AD', 'FD', 'DBA'}
>>> set_job.pop() # 随机删除一个元素
'QA'
>>> print(set_job)
{'HR', 'MD', 'DEV', 'Sales', 'OPS', 'AD', 'FD', 'DBA'}
>>> set_job.discard('OPS') # 指定删除
>>> set_job.discard('xxx') # 不存在返回None,不会报KeyError
>>> print(set_job)
{'HR', 'MD', 'DEV', 'Sales', 'AD', 'FD', 'DBA'}

其他:
>>> set_job = {'QA', 'HR', 'PD', 'Sales', 'DEV', 'MD', 'OPS', 'AD', 'FD', 'DBA'}
>>> len(set_job)  # 集合长度
10
>>> 'QA' in set_job  # 判断是否在集合中
True
>>> 'XXX' not in set_job # 不在集合中
True
>>> for i in set_job:   # 循环
...     print(i)


集合关系测试


交集:
intercaiton.png
>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> print(set_a.intersection(set_b)) # 常规方式
{5, 6}
>>> print(set_a & set_b) # 运算符(&)方式
{5, 6}

并集
bingji.png
>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = set_a.union(set_b)    # 关键字union做并集运算 先后顺序无关,谁并谁都可以
>>> print(set_c)
{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}
>>> 
>>> set_c = set_a | set_b     # 运算符关键符 | 做并集运算  先后顺序无关,谁并谁都可以
>>> print(set_c)
{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}

差集
chaji.png
>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = set_a - set_b # a集合跟b集合做差集 关键符 -
>>> print(set_c)
{8, 9, 10, 7}
>>> set_d = set_b - set_a # b集合跟a集合做差集 关键符 -
>>> print(set_d)
{1, 2, 3, 4}
>>> set_c = set_a.difference(set_b) # a集合跟b集合做差集 关键字difference
>>> print(set_c)
{8, 9, 10, 7}
>>> set_d = set_b.difference(set_a) # b集合跟a集合做差集 关键字difference
>>> print(set_d)
{1, 2, 3, 4}

 
子集父集
fuziji.png

拿苹果来打比方就是,把苹果掰开,然后掰开的一小部分就是子集,然后整个苹果就是父集
>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = {7, 8, 9, 10}
>>> set_d = {1, 2, 3, 4}
>>> set_e = {5, 6}
>>> set_f = {11, 12, 13, 14, 15, 16}
>>> set_c.issubset(set_a) # 测试集合c是否是集合a的子集 放回布尔值 关键字issubset
True
>>> set_d.issubset(set_b) # 测试集合d是否是集合b的子集 返回布尔值 issubset
True
>>> set_e.issubset(set_a)
True
>>> set_e.issubset(set_b)
True
>>> set_e <= set_a # 测试集合e是否是集合a的子集 关键符 <=
True
>>> set_e <= set_b
True
>>> set_f.issuperset(set_a) # 测试f集合是否是a集合的父集
False
>>> set_a.issuperset(set_e) # 测试a集合是否是集合e的父集 关键字issuperset
True
>>> set_b >= set_e # 测试集合b是否是集合e的父集 关键符 >=
True
>>> set_b >= set_d
True

对称差集
对称差集就是两个集合去掉相同的部分,然后剩下的所有元素组成的集合
duichengchaji.png
>>> set_a = {5, 6, 7, 8, 9, 10}
>>> set_b = {1, 2, 3, 4, 5, 6}
>>> set_c = set_a.symmetric_difference(set_b) # 集合a和集合b做对称差集 关键字symmetric_difference
>>> print(set_c)
{1, 2, 3, 4, 7, 8, 9, 10}
>>> set_c = set_a ^ set_b # 集合a和集合b做对称差集 关键符 ^
>>> print(set_c)
{1, 2, 3, 4, 7, 8, 9, 10}
>>> set_c = set_b ^ set_a
>>> print(set_c)
{1, 2, 3, 4, 7, 8, 9, 10}

所有方法:
class set(object):
"""
set() -> new empty set object
set(iterable) -> new set object

Build an unordered collection of unique elements.
"""
def add(self, *args, **kwargs): # real signature unknown
"""
Add an element to a set.

This has no effect if the element is already present.
"""
pass

def clear(self, *args, **kwargs): # real signature unknown
""" Remove all elements from this set. """
pass

def copy(self, *args, **kwargs): # real signature unknown
""" Return a shallow copy of a set. """
pass

def difference(self, *args, **kwargs): # real signature unknown
"""
Return the difference of two or more sets as a new set.

(i.e. all elements that are in this set but not the others.)
"""
pass

def difference_update(self, *args, **kwargs): # real signature unknown
""" Remove all elements of another set from this set. """
pass

def discard(self, *args, **kwargs): # real signature unknown
"""
Remove an element from a set if it is a member.

If the element is not a member, do nothing.
"""
pass

def intersection(self, *args, **kwargs): # real signature unknown
"""
Return the intersection of two sets as a new set.

(i.e. all elements that are in both sets.)
"""
pass

def intersection_update(self, *args, **kwargs): # real signature unknown
""" Update a set with the intersection of itself and another. """
pass

def isdisjoint(self, *args, **kwargs): # real signature unknown
""" Return True if two sets have a null intersection. """
pass

def issubset(self, *args, **kwargs): # real signature unknown
""" Report whether another set contains this set. """
pass

def issuperset(self, *args, **kwargs): # real signature unknown
""" Report whether this set contains another set. """
pass

def pop(self, *args, **kwargs): # real signature unknown
"""
Remove and return an arbitrary set element.
Raises KeyError if the set is empty.
"""
pass

def remove(self, *args, **kwargs): # real signature unknown
"""
Remove an element from a set; it must be a member.

If the element is not a member, raise a KeyError.
"""
pass

def symmetric_difference(self, *args, **kwargs): # real signature unknown
"""
Return the symmetric difference of two sets as a new set.

(i.e. all elements that are in exactly one of the sets.)
"""
pass

def symmetric_difference_update(self, *args, **kwargs): # real signature unknown
""" Update a set with the symmetric difference of itself and another. """
pass

def union(self, *args, **kwargs): # real signature unknown
"""
Return the union of sets as a new set.

(i.e. all elements that are in either set.)
"""
pass

def update(self, *args, **kwargs): # real signature unknown
""" Update a set with the union of itself and others. """
pass

Python菜鸟之路基础篇(一)

编程语言采菊篱下 发表了文章 • 3 个评论 • 1143 次浏览 • 2016-07-26 00:55 • 来自相关话题

Hello World

学习任何一门语言,我想大家写的以一句就是hello world吧,下面我们来看看Python的hello world
创建一个hello.py的文件:print ("Hello World")然后执行命令:python hello.py ,输出crh:Python crh$ python3 hello.py
Hello World
 
Python执行过程为: 把代码读到内存 ---->词法语法分析 ---->放到编译器 ----> 生成字节码 ---->执行字节码 ---->生成机器码---->CPU执行,图示如下:




指定解释器
在上面情况,我们指定Python3 来执行hello.py
如果想要类似于执行shell脚本一样执行python脚本,例: ./hello.py ,那么就需要在 hello.py 文件的头部指定解释器,如下:crh:Python crh$ cat hello.py
#!/usr/bin/env python3

print ("Hello World")像上面这样,然后给hello.py文件添加执行权限(chmod +x hello.py)就可以像执行shell脚本一样./hello.py 即可。
***像上面是利用Linux env命令通过环境变量去找到你想用的Python命令,如果你指定用某个Python版本的话一可以写绝对路径,比如:/usr/bin/python or /usr/local/bin/python3
 
在交互器中执行
除了把程序写在文件里,还可以直接调用python自带的交互器运行代码,进行调试和测试crh:Python crh$ python3
Python 3.5.1 (default, Dec 26 2015, 18:08:53)
[GCC 4.2.1 Compatible Apple LLVM 7.0.2 (clang-700.1.81)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
[quote]>> print ("Hello World")
Hello World
>>>  

变量

在一个计算机程序中引用变量是用来存储信息和操作的。他们还提供一种标签数据与一个描述性的名称,所以我们的程序可以被读者和我们自己更清楚地理解。它有助于认为变量保存信息的容器。他们的唯一目的是标签和数据存储在内存中。这些数据可以通过使用程序引用。
 
声明变量#_[i]_coding:utf-8_[/i]_

name = "Lucky chen"如上面所示声明了一个变量name,他的值是"Lucky chen"
 
我们再来看一组连续赋值的过程:>>> name = "crh"
>>> name1 = name
>>> print (name,name1)
crh crh
>>> name = "Lucky"
>>> print (name1,name)
crh Lucky如上所示,为什么name1 = name 当后续把name变量的值改变了,为什么name1的值没有随着改变呢,如下看看你就明白了:>>> name = "crh" #首先在内存中打开一块内存空间存储name变量值
>>> id(name) #查看变量name的内存地址
4412833952
>>> name1 = name #把我们把name赋值给name1变量
>>> id(name1) #然后查看name1变量的内存地址 (跟name变量的内存地址一样)
4412833952
>>> name = "lucky" #重新打开一个内存空间存储name的变量值
>>> id(name) #查看新的name变量值的内存地址
4412834176
>>> id(name1) #查看name1变量内存地址
4412833952如上所示,我们可以看出,nama1其实就是借助name变量做一个变量的赋值,通过name变量得到值所在内存中的内存地址后,从而变成了一个正常的赋值过程。而不换随着name变量的内存空间地址的改变而改变。示意图如下:





交互输入

用户输入就是程序和用户的交互,程序等待用户输入一个参数然后重新继续进行:#!/usr/bin/env python3
#Authe: Lucky.chen
#_[i]_coding:utf-8_[/i]_

name = input("Please enter your name:")
print ("[size=16]#",name,"[/size]#")



如上图所示,默认Python3下的input函数用户输入的所有东西都当做字符串处理,所以你输入的年龄希望它是整数类型,还需要int()一下。
 
在python2中input这个函数,用户默认输入的是什么格式的参数,Python就当作是什么类型处理,Python2中获取用户输入参数的函数还有一个叫做raw_input(),这个函数默认也是字符串处理。可以看出Python3为了简洁统一,在Python3中已经不存在了raw_input()函数,input()一个函数完全可以做到所有使用。
 
平常如果我们用针对密码、密码串之类的交互的话,一般用户的输入时隐藏或者*****的,输入密码时,在Python下如果你需要你输入的东西不可见,可以利用getpass 模块中的 getpass方法来处理:#!/usr/bin/env python3
#Authe: Lucky.chen
#_[i]_coding:utf-8_[/i]_[/quote]

#导入getpass模块
import getpass

# 将用户输入的内容赋值给 name 变量
pwd = getpass.getpass("请输入密码:")

# 打印输入的内容
print("Password is [size=16]",pwd,"***print end")[/size]

#比如我输入110119,执行过程和结果如下:
请输入密码:
Password is [size=16] 110119 ***print end[/size]

注释和拼接

注释:
单行注释:# 开头就好,跟shell一样
多行注释:成对的三个单引号 ''' 注释内容 ''' 或者 成对的三个双引号 """  注释内容  """>>> ''' My name is lucky '''
' My name is lucky '
[quote]>> """ My age is 23 """
' My age is 23 '
>>> # Good Idea
...
>>> msg = """ My info is :
... age: 23
... name: lucky
... job: IT"""
>>> print (msg)
My info is :
age: 23
name: lucky
job: IT
>>>
 
拼接:
1、难受的 "+" >>> name = "lucky"
>>> age = 23
>>> job = "IT"
>>>
>>> msg = """ Info of """ +name + """
... Name:""" +name + """
... Age:""" +age + """
... Job:""" +job
Traceback (most recent call last):
File "<stdin>", line 4, in <module>
TypeError: Can't convert 'int' object to str implicitly
>>>
>>> name = "lucky"
>>> age = "23"
>>> job = "IT"
>>> msg = """ Info of """ +name + """
... Name:""" +name + """
... Age:""" +age + """
... Job:""" +job
>>> print (msg)
Info of lucky
Name:lucky
Age:23
Job:IT
>>> 如上所示 "+"拼接只能是字符串,如果是整型、或者是浮点都会报错。
 
2、百分号(%)
 Code:#!/usr/bin/env python3.5
#auther: lucky.chen[/quote]

name = input("Please input your name: ")
age = input("Please input your age:")
job = input("Please input your job:")
salary = input("Please input your salary:")

msg = """------------ info of %s
Name: %s
Age: %s
Job: %s
Salary: %s
""" % (name,name,age,job,salary)

print (msg)Result:Please input your name: lucky
Please input your age:23
Please input your job:IT
Please input your salary:40000
------------ info of lucky
Name: lucky
Age: 23
Job: IT
Salary: 40000
 3、使用format函数
情况一:使用变量格式化
Code:#!/usr/bin/env python3.5
#auther: lucky.chen

name = input("Please input your name: ")
age = input("Please input your age:")
job = input("Please input your job:")
salary = input("Please input your salary:")

msg = """------------ info of {_Name}
Name: {_Name}
Age: {_Age}
Job: {_Job}
Salary: {_Salary}
""".format(_Name=name,_Age=age,_Job=job,_Salary=salary)

print (msg)Result:Please input your name: crh
Please input your age:23
Please input your job:IT
Please input your salary:45000
------------ info of crh
Name: crh
Age: 23
Job: IT
Salary: 45000情况二:使用下脚标#!/usr/bin/env python3.5
#auther: lucky.chen

name = input('please input your name:')
age = input('please input your age:')
job = input('please input your job:')
salary = input('please input your salary:')
msg = '''
------------info of {0}-----------
Name: {0}
Age: {1}
Job: {2}
Salary: {3}
'''.format(name,age,job,salary)
print (msg)Result:please input your name:chenronghua
please input your age:23
please input your job:OPS
please input your salary:50000

------------info of chenronghua-----------
Name: chenronghua
Age: 23
Job: OPS
Salary: 50000format是比较好的方式,有时候我们必须使用format方法,所以掌握了format就好。
 

流程控制

一、流程控制这里先介绍 if ...... else  and if ...... elif ..... else 
 
1、if ..... else(用户认证登录)
Code:#!/usr/bin/env python3.5
#auther: lucky.chen

name = input("Please input your name:")
passwd = input("Please input your password:")

if name == "crh" and passwd == "123456":
print (" \033[32mWelcome login OPS Management platform\033[0m ")
else:
print ("\033[31mYour UserName or Password Error\033[0m")Result:Please input your name:crh
Please input your password:34
Your UserName or Password Error
 2、if ..... elfi ...... else
Code:#!/usr/bin/env python3.5
#auther: lucky.chen

age = int(input("Pleast input your age:"))

if age < 18:
print (" \033[32m You're too young \033[0m ")
elif age > 18 and age < 30:
print ("\033[31m You still have many chance comes at a time when youth waiting for you \033[0m")
else:
print ("\033[33m Before you is too old to do \033[0m")Result:Pleast input your age:23
You still have many chance comes at a time when youth waiting for you
 二、for 循环遍历#!/usr/bin/env python3.5
#auther: lucky.chen

for num in range(5):
print ("loop is:",num)

# Result is:
loop is: 0
loop is: 1
loop is: 2
loop is: 3
loop is: 4range函数也可以设置步长值,比如我们要打印出1-10中的所有偶数(默认步长为1)#!/usr/bin/env python3.5
#auther: lucky.chen

for num in range(0,11,2):
print ("loop is:",num)

# Result
loop is: 0
loop is: 2
loop is: 4
loop is: 6
loop is: 8
loop is: 10除掉range函数我们还可以使用xrange函数,为什么要这里要介绍xrange呢,因为xrange相对于range来说性能比较优越,因为xrange不需要一上来就开辟一块很大的内存空间,具体可以参考我之前发布的文章:Python中xrange和range的异同 ,但是好像Python3.*中没有了xrange函数。
 
for...else...循环介绍,不止if中有else,在for循环中也是可以用else的,在for循环中的else就是当前面的循环正常执行完后,没有跳出,后面的else代码将被执行。crh:Python crh$ cat for.py
#!/usr/bin/env python3
#Auther: lucky.chen

for num in range(4):
print ("Loop is:",num)
else:
print ("normal")
crh:Python crh$ ./for.py
Loop is: 0
Loop is: 1
Loop is: 2
Loop is: 3
normal
crh:Python crh$ crh:Python crh$ cat for.py
#!/usr/bin/env python3
#Auther: lucky.chen

for num in range(4):
if num > 2:
break
print ("Loop is:",num)
else:
print ("normal")
crh:Python crh$ ./for.py
Loop is: 0
Loop is: 1
Loop is: 2
crh:Python crh$三、while循环遍历
 
while 循环它的原理是:当条件为真的时候运行,当条件为假的时候停止!没有一个规定次数,不设置条件就永远循环下去。#!/usr/bin/env python3.5
#auther: lucky.chen

import time
count = 0
while True:
count +=1
print ("loop",count)
time.sleep(3)
#这个循环3秒钟自+1后,无线循环只要这个条件为”真“,就无限循环下去#!/usr/bin/env python3.5
#auther: lucky.chen

import time
num = 0

while num < 3:
num +=1
print ("Num is:",num)
time.sleep(3)

#这个循环每3秒循环一次,当条件num < 3的时候为真(自己设置的条件),当num不小于3的时候为假(false)循环停止.While ...... else#!/usr/bin/env python3.5
#auther: lucky.chen

while 1:
if num == 4:
print ("I think stop")
break
print (num)
num += 1
else:
print ("stop")
 四、break和continue介绍break在循环中的作用是跳出所在的循环体,不在进行循环,而continue是跳出所在循环体中的本次循环,后续没有完的循环继续。Code:#!/usr/bin/env python3.5
#auther: lucky.chen

num = 1

print ("test break for loop start")
for n in range(5):
if n == num:
break
print (n)

print ("\n")

print ("test continue for loop start")
for n in range(5):
if n == num:
continue
print (n)Result:test break for loop start
0


test continue for loop start
0
2
3
4
猜数字游戏:#!/usr/bin/env python3.5
#auther: lucky.chen

#load module (random)
import random

TryNum = 0
RandNum = random.randrange(10)
print (RandNum)


while TryNum < 3:
GuessNum = int(input("请猜测从0到9之间的一个中奖数字:"))

if GuessNum >= 10:
print ("你输入的数字不在中奖号码范围内,请重新输入!")
continue

if GuessNum == RandNum:
print ("恭喜你猜对了,你将获得小米电视一台!")
break

elif GuessNum > RandNum:
print ("你猜的数字太大了可以再往小了猜")

else:
print ("你猜的数字太小了可以往大了猜")

TryNum += 1

else:
print ("不好意思你三次机会用完了,Game over!")

#先随机到0-9中筛选出以为数字,然后用户三次机会猜测一个中奖号码,如果用户输入的数字不在范围内,则让用户再次输入.Result:4
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:2
你猜的数字太小了可以往大了猜
请猜测从0到9之间的一个中奖数字:5
你猜的数字太大了可以再往小了猜
请猜测从0到9之间的一个中奖数字:4
恭喜你猜对了,你将获得小米电视一台!

 
五、嵌套循环
While for:#!/usr/bin/env python3.5
#auther: lucky.chen

count = 1

while count < 4:
print("count var lt 4")

print ("#########################[size=16]#")[/size]

for n in range(3):
print ("for num is:",n)

print ("****************************")
count += 1Result:count var lt 4
#########################[size=16]#[/size]
for num is: 0
for num is: 1
for num is: 2
****************************
count var lt 4
#########################[size=16]#[/size]
for num is: 0
for num is: 1
for num is: 2
****************************
count var lt 4
#########################[size=16]#[/size]
for num is: 0
for num is: 1
for num is: 2
****************************
 死循环:#!/usr/bin/env python3.5
#auther: lucky.chen
import time

while True:
print ("One Loop")
time.sleep(1)

while True:
print ("Two Loop")
time.sleep(1)

while True:
print ("Three Loop")
time.sleep(1)
#这是一个死循环,第一次执行这段code的时候,依次往下执行,单到了第三个while的时候,就一直是true,所以一直在执行第三个while下的code.

#结果如下:
One Loop
Two Loop
Three Loop
Three Loop
Three Loop
Three Loop
..........
..........如上我们给出了一个死循环的例子,但是如果如果我们需要跳出循环应该怎么做,如果用break可以做到吗?
1、第一个while后加break分析




 
2、第二个while后加break分析




 
3、第三个while后加break分析




 
既然存在这种死循环的那我们有什么办法可以跳出呢?那就是打标志,标志位
Code:#!/usr/bin/env python3.5
#auther: lucky.chen

count = 0
while True:
print ("我是第一层")
jump_1_flag = False

while True:
print ("我是第二层")
jump_2_flag = False

while True:
count += 1
print ("我是第三层")

if count > 3:
jump_2_flag = True
break

if jump_2_flag:
print ("第三层跳到我这里来了,我也要跳到第一层")
jump_1_flag = True
break

if jump_1_flag:
print ("第二层和第三层跳到第一层了,我也要跳")
break分析和结果: 查看全部


Hello World


学习任何一门语言,我想大家写的以一句就是hello world吧,下面我们来看看Python的hello world
创建一个hello.py的文件:
print ("Hello World")
然后执行命令:python hello.py ,输出
crh:Python crh$ python3 hello.py 
Hello World

 
Python执行过程为: 把代码读到内存 ---->词法语法分析 ---->放到编译器 ----> 生成字节码 ---->执行字节码 ---->生成机器码---->CPU执行,图示如下:
workfollow.png

指定解释器
在上面情况,我们指定Python3 来执行hello.py
如果想要类似于执行shell脚本一样执行python脚本,例: ./hello.py ,那么就需要在 hello.py 文件的头部指定解释器,如下:
crh:Python crh$ cat hello.py 
#!/usr/bin/env python3

print ("Hello World")
像上面这样,然后给hello.py文件添加执行权限(chmod +x hello.py)就可以像执行shell脚本一样./hello.py 即可。
***像上面是利用Linux env命令通过环境变量去找到你想用的Python命令,如果你指定用某个Python版本的话一可以写绝对路径,比如:/usr/bin/python or /usr/local/bin/python3
 
在交互器中执行
除了把程序写在文件里,还可以直接调用python自带的交互器运行代码,进行调试和测试
crh:Python crh$ python3
Python 3.5.1 (default, Dec 26 2015, 18:08:53)
[GCC 4.2.1 Compatible Apple LLVM 7.0.2 (clang-700.1.81)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
[quote]>> print ("Hello World")
Hello World
>>>
 


变量


在一个计算机程序中引用变量是用来存储信息和操作的。他们还提供一种标签数据与一个描述性的名称,所以我们的程序可以被读者和我们自己更清楚地理解。它有助于认为变量保存信息的容器。他们的唯一目的是标签和数据存储在内存中。这些数据可以通过使用程序引用。
 
声明变量
#_[i]_coding:utf-8_[/i]_

name = "Lucky chen"
如上面所示声明了一个变量name,他的值是"Lucky chen"
 
我们再来看一组连续赋值的过程:
>>> name = "crh"
>>> name1 = name
>>> print (name,name1)
crh crh
>>> name = "Lucky"
>>> print (name1,name)
crh Lucky
如上所示,为什么name1 = name 当后续把name变量的值改变了,为什么name1的值没有随着改变呢,如下看看你就明白了:
>>> name = "crh"     #首先在内存中打开一块内存空间存储name变量值
>>> id(name) #查看变量name的内存地址
4412833952
>>> name1 = name #把我们把name赋值给name1变量
>>> id(name1) #然后查看name1变量的内存地址 (跟name变量的内存地址一样)
4412833952
>>> name = "lucky" #重新打开一个内存空间存储name的变量值
>>> id(name) #查看新的name变量值的内存地址
4412834176
>>> id(name1) #查看name1变量内存地址
4412833952
如上所示,我们可以看出,nama1其实就是借助name变量做一个变量的赋值,通过name变量得到值所在内存中的内存地址后,从而变成了一个正常的赋值过程。而不换随着name变量的内存空间地址的改变而改变。示意图如下:
var.png


交互输入


用户输入就是程序和用户的交互,程序等待用户输入一个参数然后重新继续进行:
#!/usr/bin/env python3
#Authe: Lucky.chen
#_[i]_coding:utf-8_[/i]_

name = input("Please enter your name:")
print ("[size=16]#",name,"[/size]#")
input.png

如上图所示,默认Python3下的input函数用户输入的所有东西都当做字符串处理,所以你输入的年龄希望它是整数类型,还需要int()一下。
 
在python2中input这个函数,用户默认输入的是什么格式的参数,Python就当作是什么类型处理,Python2中获取用户输入参数的函数还有一个叫做raw_input(),这个函数默认也是字符串处理。可以看出Python3为了简洁统一,在Python3中已经不存在了raw_input()函数,input()一个函数完全可以做到所有使用。
 
平常如果我们用针对密码、密码串之类的交互的话,一般用户的输入时隐藏或者*****的,输入密码时,在Python下如果你需要你输入的东西不可见,可以利用getpass 模块中的 getpass方法来处理:
#!/usr/bin/env python3
#Authe: Lucky.chen
#_[i]_coding:utf-8_[/i]_[/quote]

#导入getpass模块
import getpass

# 将用户输入的内容赋值给 name 变量
pwd = getpass.getpass("请输入密码:")

# 打印输入的内容
print("Password is [size=16]",pwd,"***print end")[/size]

#比如我输入110119,执行过程和结果如下:
请输入密码:
Password is [size=16] 110119 ***print end
[/size]


注释和拼接


注释:
单行注释:# 开头就好,跟shell一样
多行注释:成对的三个单引号 ''' 注释内容 ''' 或者 成对的三个双引号 """  注释内容  """
>>> ''' My name is lucky ''' 
' My name is lucky '
[quote]>> """ My age is 23 """
' My age is 23 '
>>> # Good Idea
...
>>> msg = """ My info is :
... age: 23
... name: lucky
... job: IT"""
>>> print (msg)
My info is :
age: 23
name: lucky
job: IT
>>>
 
拼接:
1、难受的 "+" 
>>> name = "lucky"
>>> age = 23
>>> job = "IT"
>>>
>>> msg = """ Info of """ +name + """
... Name:""" +name + """
... Age:""" +age + """
... Job:""" +job
Traceback (most recent call last):
File "<stdin>", line 4, in <module>
TypeError: Can't convert 'int' object to str implicitly
>>>
>>> name = "lucky"
>>> age = "23"
>>> job = "IT"
>>> msg = """ Info of """ +name + """
... Name:""" +name + """
... Age:""" +age + """
... Job:""" +job
>>> print (msg)
Info of lucky
Name:lucky
Age:23
Job:IT
>>>
如上所示 "+"拼接只能是字符串,如果是整型、或者是浮点都会报错。
 
2、百分号(%)
 Code:
#!/usr/bin/env python3.5
#auther: lucky.chen[/quote]

name = input("Please input your name: ")
age = input("Please input your age:")
job = input("Please input your job:")
salary = input("Please input your salary:")

msg = """------------ info of %s
Name: %s
Age: %s
Job: %s
Salary: %s
""" % (name,name,age,job,salary)

print (msg)
Result:
Please input your name: lucky
Please input your age:23
Please input your job:IT
Please input your salary:40000
------------ info of lucky
Name: lucky
Age: 23
Job: IT
Salary: 40000

 3、使用format函数
情况一:使用变量格式化
Code:
#!/usr/bin/env python3.5
#auther: lucky.chen

name = input("Please input your name: ")
age = input("Please input your age:")
job = input("Please input your job:")
salary = input("Please input your salary:")

msg = """------------ info of {_Name}
Name: {_Name}
Age: {_Age}
Job: {_Job}
Salary: {_Salary}
""".format(_Name=name,_Age=age,_Job=job,_Salary=salary)

print (msg)
Result:
Please input your name: crh
Please input your age:23
Please input your job:IT
Please input your salary:45000
------------ info of crh
Name: crh
Age: 23
Job: IT
Salary: 45000
情况二:使用下脚标
#!/usr/bin/env python3.5
#auther: lucky.chen

name = input('please input your name:')
age = input('please input your age:')
job = input('please input your job:')
salary = input('please input your salary:')
msg = '''
------------info of {0}-----------
Name: {0}
Age: {1}
Job: {2}
Salary: {3}
'''.format(name,age,job,salary)
print (msg)
Result:
please input your name:chenronghua
please input your age:23
please input your job:OPS
please input your salary:50000

------------info of chenronghua-----------
Name: chenronghua
Age: 23
Job: OPS
Salary: 50000
format是比较好的方式,有时候我们必须使用format方法,所以掌握了format就好。
 


流程控制


一、流程控制这里先介绍 if ...... else  and if ...... elif ..... else 
 
1、if ..... else(用户认证登录)
Code:
#!/usr/bin/env python3.5
#auther: lucky.chen

name = input("Please input your name:")
passwd = input("Please input your password:")

if name == "crh" and passwd == "123456":
print (" \033[32mWelcome login OPS Management platform\033[0m ")
else:
print ("\033[31mYour UserName or Password Error\033[0m")
Result:
Please input your name:crh
Please input your password:34
Your UserName or Password Error

 2、if ..... elfi ...... else
Code:
#!/usr/bin/env python3.5
#auther: lucky.chen

age = int(input("Pleast input your age:"))

if age < 18:
print (" \033[32m You're too young \033[0m ")
elif age > 18 and age < 30:
print ("\033[31m You still have many chance comes at a time when youth waiting for you \033[0m")
else:
print ("\033[33m Before you is too old to do \033[0m")
Result:
Pleast input your age:23
You still have many chance comes at a time when youth waiting for you

 二、for 循环遍历
#!/usr/bin/env python3.5
#auther: lucky.chen

for num in range(5):
print ("loop is:",num)

# Result is:
loop is: 0
loop is: 1
loop is: 2
loop is: 3
loop is: 4
range函数也可以设置步长值,比如我们要打印出1-10中的所有偶数(默认步长为1)
#!/usr/bin/env python3.5
#auther: lucky.chen

for num in range(0,11,2):
print ("loop is:",num)

# Result
loop is: 0
loop is: 2
loop is: 4
loop is: 6
loop is: 8
loop is: 10
除掉range函数我们还可以使用xrange函数,为什么要这里要介绍xrange呢,因为xrange相对于range来说性能比较优越,因为xrange不需要一上来就开辟一块很大的内存空间,具体可以参考我之前发布的文章:Python中xrange和range的异同 ,但是好像Python3.*中没有了xrange函数。
 
for...else...循环介绍,不止if中有else,在for循环中也是可以用else的,在for循环中的else就是当前面的循环正常执行完后,没有跳出,后面的else代码将被执行。
crh:Python crh$ cat for.py 
#!/usr/bin/env python3
#Auther: lucky.chen

for num in range(4):
print ("Loop is:",num)
else:
print ("normal")
crh:Python crh$ ./for.py
Loop is: 0
Loop is: 1
Loop is: 2
Loop is: 3
normal
crh:Python crh$
crh:Python crh$ cat for.py 
#!/usr/bin/env python3
#Auther: lucky.chen

for num in range(4):
if num > 2:
break
print ("Loop is:",num)
else:
print ("normal")
crh:Python crh$ ./for.py
Loop is: 0
Loop is: 1
Loop is: 2
crh:Python crh$
三、while循环遍历
 
while 循环它的原理是:当条件为真的时候运行,当条件为假的时候停止!没有一个规定次数,不设置条件就永远循环下去。
#!/usr/bin/env python3.5
#auther: lucky.chen

import time
count = 0
while True:
count +=1
print ("loop",count)
time.sleep(3)
#这个循环3秒钟自+1后,无线循环只要这个条件为”真“,就无限循环下去
#!/usr/bin/env python3.5
#auther: lucky.chen

import time
num = 0

while num < 3:
num +=1
print ("Num is:",num)
time.sleep(3)

#这个循环每3秒循环一次,当条件num < 3的时候为真(自己设置的条件),当num不小于3的时候为假(false)循环停止.
While ...... else
#!/usr/bin/env python3.5
#auther: lucky.chen

while 1:
if num == 4:
print ("I think stop")
break
print (num)
num += 1
else:
print ("stop")

 四、break和continue介绍
break在循环中的作用是跳出所在的循环体,不在进行循环,而continue是跳出所在循环体中的本次循环,后续没有完的循环继续。
Code:
#!/usr/bin/env python3.5
#auther: lucky.chen

num = 1

print ("test break for loop start")
for n in range(5):
if n == num:
break
print (n)

print ("\n")

print ("test continue for loop start")
for n in range(5):
if n == num:
continue
print (n)
Result:
test break for loop start
0


test continue for loop start
0
2
3
4

猜数字游戏:
#!/usr/bin/env python3.5
#auther: lucky.chen

#load module (random)
import random

TryNum = 0
RandNum = random.randrange(10)
print (RandNum)


while TryNum < 3:
GuessNum = int(input("请猜测从0到9之间的一个中奖数字:"))

if GuessNum >= 10:
print ("你输入的数字不在中奖号码范围内,请重新输入!")
continue

if GuessNum == RandNum:
print ("恭喜你猜对了,你将获得小米电视一台!")
break

elif GuessNum > RandNum:
print ("你猜的数字太大了可以再往小了猜")

else:
print ("你猜的数字太小了可以往大了猜")

TryNum += 1

else:
print ("不好意思你三次机会用完了,Game over!")

#先随机到0-9中筛选出以为数字,然后用户三次机会猜测一个中奖号码,如果用户输入的数字不在范围内,则让用户再次输入.
Result:
4
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:11
你输入的数字不在中奖号码范围内,请重新输入!
请猜测从0到9之间的一个中奖数字:2
你猜的数字太小了可以往大了猜
请猜测从0到9之间的一个中奖数字:5
你猜的数字太大了可以再往小了猜
请猜测从0到9之间的一个中奖数字:4
恭喜你猜对了,你将获得小米电视一台!

 
五、嵌套循环
While for:
#!/usr/bin/env python3.5
#auther: lucky.chen

count = 1

while count < 4:
print("count var lt 4")

print ("#########################[size=16]#")[/size]

for n in range(3):
print ("for num is:",n)

print ("****************************")
count += 1
Result:
count var lt 4
#########################[size=16]#[/size]
for num is: 0
for num is: 1
for num is: 2
****************************
count var lt 4
#########################[size=16]#[/size]
for num is: 0
for num is: 1
for num is: 2
****************************
count var lt 4
#########################[size=16]#[/size]
for num is: 0
for num is: 1
for num is: 2
****************************

 死循环:
#!/usr/bin/env python3.5
#auther: lucky.chen
import time

while True:
print ("One Loop")
time.sleep(1)

while True:
print ("Two Loop")
time.sleep(1)

while True:
print ("Three Loop")
time.sleep(1)
#这是一个死循环,第一次执行这段code的时候,依次往下执行,单到了第三个while的时候,就一直是true,所以一直在执行第三个while下的code.

#结果如下:
One Loop
Two Loop
Three Loop
Three Loop
Three Loop
Three Loop
..........
..........
如上我们给出了一个死循环的例子,但是如果如果我们需要跳出循环应该怎么做,如果用break可以做到吗?
1、第一个while后加break分析
loop1.png

 
2、第二个while后加break分析
loop2.png

 
3、第三个while后加break分析
loop3.png

 
既然存在这种死循环的那我们有什么办法可以跳出呢?那就是打标志,标志位
Code:
#!/usr/bin/env python3.5
#auther: lucky.chen

count = 0
while True:
print ("我是第一层")
jump_1_flag = False

while True:
print ("我是第二层")
jump_2_flag = False

while True:
count += 1
print ("我是第三层")

if count > 3:
jump_2_flag = True
break

if jump_2_flag:
print ("第三层跳到我这里来了,我也要跳到第一层")
jump_1_flag = True
break

if jump_1_flag:
print ("第二层和第三层跳到第一层了,我也要跳")
break
分析和结果:
tags.png

Python input和raw_input的区别

编程语言采菊篱下 发表了文章 • 1 个评论 • 1062 次浏览 • 2015-12-14 23:18 • 来自相关话题

使用input和raw_input都可以读取控制台的输入,但是input和raw_input在处理数字时是有区别的

纯数字输入

当输入为纯数字时
[]input返回的是数值类型,如int,float[/][]raw_inpout返回的是字符串类型,string类型[/]





输入字符串为表达式

input会计算在字符串中的数字表达式,而raw_input不会。
如输入 "57 + 3":
input会得到整数60
raw_input会得到字符串"57 + 3"




输入字符串结果如下:




通过上面的实验我们知道input它会根据用户输入变换相应的类型,而且如果要输入字符和字符串的时候必须要用引号包起来,而raw_input则是不管用户输入什么类型的都会转变成字符型.

python input的实现

看python input的文档,你可以发现input其实是通过raw_input来实现的,原理很简单,就下面一行代码:def input(prompt):
return (eval(raw_input(prompt))) 查看全部
使用input和raw_input都可以读取控制台的输入,但是input和raw_input在处理数字时是有区别的


纯数字输入


当输入为纯数字时
    []input返回的是数值类型,如int,float[/][]raw_inpout返回的是字符串类型,string类型[/]

cb.png


输入字符串为表达式


input会计算在字符串中的数字表达式,而raw_input不会。
如输入 "57 + 3":
input会得到整数60
raw_input会得到字符串"57 + 3"
cb1.png

输入字符串结果如下:
cb3.png

通过上面的实验我们知道input它会根据用户输入变换相应的类型,而且如果要输入字符和字符串的时候必须要用引号包起来,而raw_input则是不管用户输入什么类型的都会转变成字符型.


python input的实现


python input的文档,你可以发现input其实是通过raw_input来实现的,原理很简单,就下面一行代码:
def input(prompt):
return (eval(raw_input(prompt)))

Python在生产环境都可以用来做什么?

编程语言koyo 回复了问题 • 2 人关注 • 3 个回复 • 2318 次浏览 • 2015-12-14 14:45 • 来自相关话题

为什么越来越多人喜欢全栈式开发语言 – Python

编程语言push 发表了文章 • 1 个评论 • 2299 次浏览 • 2015-11-29 20:12 • 来自相关话题

前段时间,ThoughtWorks在深圳举办一次社区活动上,有一个演讲主题叫做“Fullstack JavaScript”,是关于用JavaScript进行前端、服务器端,甚至数据库(MongoDB)开发,一个Web应用开发人员,只需要学会一门语言,就可以实现整个应用。
 
受此启发,我发现Python可以称为大数据全栈式开发语言。因为Python在云基础设施,DevOps,大数据处理等领域都是炙手可热的语言。




就像只要会JavaScript就可以写出完整的Web应用,只要会Python,就可以实现一个完整的大数据处理平台。

云基础设施

这年头,不支持云平台,不支持海量数据,不支持动态伸缩,根本不敢说自己是做大数据的,顶多也就敢跟人说是做商业智能(BI)。
 
云平台分为私有云和公有云。私有云平台如日中天的OpenStack,就是Python写的。曾经的追赶者CloudStack,在刚推出时大肆强调自己是Java写的,比Python有优势。结果,搬石砸脚,2015年初,CloudStack的发起人Citrix宣布加入OpenStack基金会,CloudStack眼看着就要寿终正寝。

如果嫌麻烦不想自己搭建私有云,用公有云,不论是AWS,GCE,Azure,还是阿里云,青云,在都提供了Python SDK,其中GCE只提供Python和JavaScript的SDK,而青云只提供Python SDK。可见各家云平台对Python的重视。

提到基础设施搭建,不得不提Hadoop,在今天,Hadoop因为其MapReduce数据处理速度不够快,已经不再作为大数据处理的首选,但是HDFS和Yarn——Hadoop的两个组件——倒是越来越受欢迎。Hadoop的开发语言是Java,没有官方提供Python支持,不过有很多第三方库封装了Hadoop的API接口(pydoop,hadoopy等等)。

Hadoop MapReduce的替代者,是号称快上100倍的Spark,其开发语言是Scala,但是提供了Scala,Java,Python的开发接口,想要讨好那么多用Python开发的数据科学家,不支持Python,真是说不过去。HDFS的替代品,比如GlusterFS,Ceph等,都是直接提供Python支持。Yarn的替代者,Mesos是C++实现,除C++外,提供了Java和Python的支持包。

DevOps

DevOps有个中文名字,叫做开发自运维。互联网时代,只有能够快速试验新想法,并在第一时间,安全、可靠的交付业务价值,才能保持竞争力。DevOps推崇的自动化构建/测试/部署,以及系统度量等技术实践,是互联网时代必不可少的。

自动化构建是因应用而易的,如果是Python应用,因为有setuptools, pip, virtualenv, tox, flake8等工具的存在,自动化构建非常简单。而且,因为几乎所有Linux系统都内置Python解释器,所以用Python做自动化,不需要系统预安装什么软件。

自动化测试方面,基于Python的Robot Framework企业级应用最喜欢的自动化测试框架,而且和语言无关。Cucumber也有很多支持者,Python对应的Lettuce可以做到完全一样的事情。Locust在自动化性能测试方面也开始受到越来越多的关注。

自动化配置管理工具,老牌的如Chef和Puppet,是Ruby开发,目前仍保持着强劲的势头。不过,新生代Ansible和SaltStack——均为Python开发——因为较前两者设计更为轻量化,受到越来越多开发这的欢迎,已经开始给前辈们制造了不少的压力。

在系统监控与度量方面,传统的Nagios逐渐没落,新贵如Sensu大受好评,云服务形式的New Relic已经成为创业公司的标配,这些都不是直接通过Python实现的,不过Python要接入这些工具,并不困难。

除了上述这些工具,基于Python,提供完整DevOps功能的PaaS平台,如Cloudify和Deis,虽未成气候,但已经得到大量关注。 

网络爬虫

大数据的数据从哪里来?除了部分企业有能力自己产生大量的数据,大部分时候,是需要靠爬虫来抓取互联网数据来做分析。

网络爬虫是Python的传统强势领域,最流行的爬虫框架Scrapy,HTTP工具包urlib2,HTML解析工具beautifulsoup,XML解析器lxml,等等,都是能够独当一面的类库。

不过,网络爬虫并不仅仅是打开网页,解析HTML这么简单。高效的爬虫要能够支持大量灵活的并发操作,常常要能够同时几千甚至上万个网页同时抓取,传统的线程池方式资源浪费比较大,线程数上千之后系统资源基本上就全浪费在线程调度上了。Python由于能够很好的支持协程(Coroutine)操作,基于此发展起来很多并发库,如Gevent,Eventlet,还有Celery之类的分布式任务框架。被认为是比AMQP更高效的ZeroMQ也是最早就提供了Python版本。有了对高并发的支持,网络爬虫才真正可以达到大数据规模。

抓取下来的数据,需要做分词处理,Python在这方面也不逊色,著名的自然语言处理程序包NLTK,还有专门做中文分词的Jieba,都是做分词的利器。

数据处理

万事俱备,只欠东风。这东风,就是数据处理算法。从统计理论,到数据挖掘,机器学习,再到最近几年提出来的深度学习理论,数据科学正处于百花齐放的时代。数据科学家们都用什么编程?

如果是在理论研究领域,R语言也许是最受数据科学家欢迎的,但是R语言的问题也很明显,因为是统计学家们创建了R语言,所以其语法略显怪异。而且R语言要想实现大规模分布式系统,还需要很长一段时间的工程之路要走。所以很多公司使用R语言做原型试验,算法确定之后,再翻译成工程语言。

Python也是数据科学家最喜欢的语言之一。和R语言不同,Python本身就是一门工程性语言,数据科学家用Python实现的算法,可以直接用在产品中,这对于大数据初创公司节省成本是非常有帮助的。正式因为数据科学家对Python和R的热爱,Spark为了讨好数据科学家,对这两种语言提供了非常好的支持。

Python的数据处理相关类库非常多。高性能的科学计算类库NumPy和SciPy,给其他高级算法打了非常好的基础,matploglib让Python画图变得像Matlab一样简单。Scikit-learn和Milk实现了很多机器学习算法,基于这两个库实现的Pylearn2,是深度学习领域的重要成员。Theano利用GPU加速,实现了高性能数学符号计算和多维矩阵计算。当然,还有Pandas,一个在工程领域已经广泛使用的大数据处理类库,其DataFrame的设计借鉴自R语言,后来又启发了Spark项目实现了类似机制。

对了,还有iPython,这个工具如此有用,以至于我差点把他当成标准库而忘了介绍。iPython是一个交互式Python运行环境,能够实时看到每一段Python代码的结果。默认情况下,iPython运行在命令行,可以执行ipython notebook在网页中运行。用matplotlib绘制的图可以直接嵌入式的显示在iPython Notebook中。
iPython Notebook的笔记本文件可以共享给其他人,这样其他人就可以在自己的环境中重现你的工作成果;如果对方没有运行环境,还可以直接转换成HTML或者PDF。




为什么是Python

正是因为应用开发工程师、运维工程师、数据科学家都喜欢Python,才使得Python成为大数据系统的全栈式开发语言。

对于开发工程师而言,Python的优雅和简洁无疑是最大的吸引力,在Python交互式环境中,执行import this,读一读Python之禅,你就明白Python为什么如此吸引人。Python社区一直非常有活力,和NodeJS社区软件包爆炸式增长不同,Python的软件包增长速度一直比较稳定,同时软件包的质量也相对较高。有很多人诟病Python对于空格的要求过于苛刻,但正是因为这个要求,才使得Python在做大型项目时比其他语言有优势。OpenStack项目总共超过200万行代码,证明了这一点。

对于运维工程师而言,Python的最大优势在于,几乎所有Linux发行版都内置了Python解释器。Shell虽然功能强大,但毕竟语法不够优雅,写比较复杂的任务会很痛苦。用Python替代Shell,做一些复杂的任务,对运维人员来说,是一次解放。

对于数据科学家而言,Python简单又不失强大。和C/C++相比,不用做很多的底层工作,可以快速进行模型验证;和Java相比,Python语法简洁,表达能力强,同样的工作只需要1/3代码;和Matlab,Octave相比,Python的工程成熟度更高。不止一个编程大牛表达过,Python是最适合作为大学计算机科学编程课程使用的语言——MIT的计算机入门课程就是使用的Python——因为Python能够让人学到编程最重要的东西——如何解决问题。

顺便提一句,微软参加2015年PyCon,高调宣布提高Python在Windows上的编程体验,包括Visual Studio支持Python,优化Python的C扩展在Windows上的编译等等。脑补下未来Python作为Windows默认组件的场景。

内容来源:ThoughtWorks洞见
分享阅读:http://insights.thoughtworkers.org/full-stack-python/ 查看全部
python_bigdata.png

前段时间,ThoughtWorks在深圳举办一次社区活动上,有一个演讲主题叫做“Fullstack JavaScript”,是关于用JavaScript进行前端、服务器端,甚至数据库(MongoDB)开发,一个Web应用开发人员,只需要学会一门语言,就可以实现整个应用。
 
受此启发,我发现Python可以称为大数据全栈式开发语言。因为Python在云基础设施,DevOps,大数据处理等领域都是炙手可热的语言。
bdlang.png

就像只要会JavaScript就可以写出完整的Web应用,只要会Python,就可以实现一个完整的大数据处理平台。


云基础设施


这年头,不支持云平台,不支持海量数据,不支持动态伸缩,根本不敢说自己是做大数据的,顶多也就敢跟人说是做商业智能(BI)。
 
云平台分为私有云和公有云。私有云平台如日中天的OpenStack,就是Python写的。曾经的追赶者CloudStack,在刚推出时大肆强调自己是Java写的,比Python有优势。结果,搬石砸脚,2015年初,CloudStack的发起人Citrix宣布加入OpenStack基金会,CloudStack眼看着就要寿终正寝。

如果嫌麻烦不想自己搭建私有云,用公有云,不论是AWS,GCE,Azure,还是阿里云,青云,在都提供了Python SDK,其中GCE只提供Python和JavaScript的SDK,而青云只提供Python SDK。可见各家云平台对Python的重视。

提到基础设施搭建,不得不提Hadoop,在今天,Hadoop因为其MapReduce数据处理速度不够快,已经不再作为大数据处理的首选,但是HDFS和Yarn——Hadoop的两个组件——倒是越来越受欢迎。Hadoop的开发语言是Java,没有官方提供Python支持,不过有很多第三方库封装了Hadoop的API接口(pydoop,hadoopy等等)。

Hadoop MapReduce的替代者,是号称快上100倍的Spark,其开发语言是Scala,但是提供了Scala,Java,Python的开发接口,想要讨好那么多用Python开发的数据科学家,不支持Python,真是说不过去。HDFS的替代品,比如GlusterFS,Ceph等,都是直接提供Python支持。Yarn的替代者,Mesos是C++实现,除C++外,提供了Java和Python的支持包。


DevOps


DevOps有个中文名字,叫做开发自运维。互联网时代,只有能够快速试验新想法,并在第一时间,安全、可靠的交付业务价值,才能保持竞争力。DevOps推崇的自动化构建/测试/部署,以及系统度量等技术实践,是互联网时代必不可少的。

自动化构建是因应用而易的,如果是Python应用,因为有setuptools, pip, virtualenv, tox, flake8等工具的存在,自动化构建非常简单。而且,因为几乎所有Linux系统都内置Python解释器,所以用Python做自动化,不需要系统预安装什么软件。

自动化测试方面,基于Python的Robot Framework企业级应用最喜欢的自动化测试框架,而且和语言无关。Cucumber也有很多支持者,Python对应的Lettuce可以做到完全一样的事情。Locust在自动化性能测试方面也开始受到越来越多的关注。

自动化配置管理工具,老牌的如Chef和Puppet,是Ruby开发,目前仍保持着强劲的势头。不过,新生代AnsibleSaltStack——均为Python开发——因为较前两者设计更为轻量化,受到越来越多开发这的欢迎,已经开始给前辈们制造了不少的压力。

在系统监控与度量方面,传统的Nagios逐渐没落,新贵如Sensu大受好评,云服务形式的New Relic已经成为创业公司的标配,这些都不是直接通过Python实现的,不过Python要接入这些工具,并不困难。

除了上述这些工具,基于Python,提供完整DevOps功能的PaaS平台,如CloudifyDeis,虽未成气候,但已经得到大量关注。 


网络爬虫


大数据的数据从哪里来?除了部分企业有能力自己产生大量的数据,大部分时候,是需要靠爬虫来抓取互联网数据来做分析。

网络爬虫是Python的传统强势领域,最流行的爬虫框架Scrapy,HTTP工具包urlib2,HTML解析工具beautifulsoup,XML解析器lxml,等等,都是能够独当一面的类库。

不过,网络爬虫并不仅仅是打开网页,解析HTML这么简单。高效的爬虫要能够支持大量灵活的并发操作,常常要能够同时几千甚至上万个网页同时抓取,传统的线程池方式资源浪费比较大,线程数上千之后系统资源基本上就全浪费在线程调度上了。Python由于能够很好的支持协程(Coroutine)操作,基于此发展起来很多并发库,如Gevent,Eventlet,还有Celery之类的分布式任务框架。被认为是比AMQP更高效的ZeroMQ也是最早就提供了Python版本。有了对高并发的支持,网络爬虫才真正可以达到大数据规模。

抓取下来的数据,需要做分词处理,Python在这方面也不逊色,著名的自然语言处理程序包NLTK,还有专门做中文分词的Jieba,都是做分词的利器。


数据处理


万事俱备,只欠东风。这东风,就是数据处理算法。从统计理论,到数据挖掘,机器学习,再到最近几年提出来的深度学习理论,数据科学正处于百花齐放的时代。数据科学家们都用什么编程?

如果是在理论研究领域,R语言也许是最受数据科学家欢迎的,但是R语言的问题也很明显,因为是统计学家们创建了R语言,所以其语法略显怪异。而且R语言要想实现大规模分布式系统,还需要很长一段时间的工程之路要走。所以很多公司使用R语言做原型试验,算法确定之后,再翻译成工程语言。

Python也是数据科学家最喜欢的语言之一。和R语言不同,Python本身就是一门工程性语言,数据科学家用Python实现的算法,可以直接用在产品中,这对于大数据初创公司节省成本是非常有帮助的。正式因为数据科学家对Python和R的热爱,Spark为了讨好数据科学家,对这两种语言提供了非常好的支持。

Python的数据处理相关类库非常多。高性能的科学计算类库NumPy和SciPy,给其他高级算法打了非常好的基础,matploglib让Python画图变得像Matlab一样简单。Scikit-learn和Milk实现了很多机器学习算法,基于这两个库实现的Pylearn2,是深度学习领域的重要成员。Theano利用GPU加速,实现了高性能数学符号计算和多维矩阵计算。当然,还有Pandas,一个在工程领域已经广泛使用的大数据处理类库,其DataFrame的设计借鉴自R语言,后来又启发了Spark项目实现了类似机制。

对了,还有iPython,这个工具如此有用,以至于我差点把他当成标准库而忘了介绍。iPython是一个交互式Python运行环境,能够实时看到每一段Python代码的结果。默认情况下,iPython运行在命令行,可以执行ipython notebook在网页中运行。用matplotlib绘制的图可以直接嵌入式的显示在iPython Notebook中。
iPython Notebook的笔记本文件可以共享给其他人,这样其他人就可以在自己的环境中重现你的工作成果;如果对方没有运行环境,还可以直接转换成HTML或者PDF。
ipython.png

为什么是Python

正是因为应用开发工程师、运维工程师、数据科学家都喜欢Python,才使得Python成为大数据系统的全栈式开发语言。

对于开发工程师而言,Python的优雅和简洁无疑是最大的吸引力,在Python交互式环境中,执行import this,读一读Python之禅,你就明白Python为什么如此吸引人。Python社区一直非常有活力,和NodeJS社区软件包爆炸式增长不同,Python的软件包增长速度一直比较稳定,同时软件包的质量也相对较高。有很多人诟病Python对于空格的要求过于苛刻,但正是因为这个要求,才使得Python在做大型项目时比其他语言有优势。OpenStack项目总共超过200万行代码,证明了这一点。

对于运维工程师而言,Python的最大优势在于,几乎所有Linux发行版都内置了Python解释器。Shell虽然功能强大,但毕竟语法不够优雅,写比较复杂的任务会很痛苦。用Python替代Shell,做一些复杂的任务,对运维人员来说,是一次解放。

对于数据科学家而言,Python简单又不失强大。和C/C++相比,不用做很多的底层工作,可以快速进行模型验证;和Java相比,Python语法简洁,表达能力强,同样的工作只需要1/3代码;和Matlab,Octave相比,Python的工程成熟度更高。不止一个编程大牛表达过,Python是最适合作为大学计算机科学编程课程使用的语言——MIT的计算机入门课程就是使用的Python——因为Python能够让人学到编程最重要的东西——如何解决问题。

顺便提一句,微软参加2015年PyCon,高调宣布提高Python在Windows上的编程体验,包括Visual Studio支持Python,优化Python的C扩展在Windows上的编译等等。脑补下未来Python作为Windows默认组件的场景。


内容来源:ThoughtWorks洞见
分享阅读:http://insights.thoughtworkers.org/full-stack-python/


python3: error while loading shared libraries: libpython3.5m.so.1.0

回复

编程语言采菊篱下 回复了问题 • 2 人关注 • 1 个回复 • 105 次浏览 • 2017-09-25 17:04 • 来自相关话题

使用Ansible会提示UserWarning: Module import pkg_resources

回复

运维技术采菊篱下 回复了问题 • 2 人关注 • 1 个回复 • 376 次浏览 • 2017-05-08 23:39 • 来自相关话题

File "collect_info.py", line 109, in <module>

回复

编程语言采菊篱下 回复了问题 • 2 人关注 • 3 个回复 • 1085 次浏览 • 2017-04-19 13:58 • 来自相关话题

老男孩Python开发2016最新14期前10周视频【限免】

回复

编程语言Target 回复了问题 • 5 人关注 • 4 个回复 • 2950 次浏览 • 2017-01-07 22:33 • 来自相关话题

python FTP问题

回复

编程语言采菊篱下 回复了问题 • 3 人关注 • 2 个回复 • 793 次浏览 • 2016-12-27 11:38 • 来自相关话题

分享个基于sendclound的邮件群发软件 大家提点意见

回复

运维技术Nappywu 发起了问题 • 1 人关注 • 0 个回复 • 703 次浏览 • 2016-11-25 15:51 • 来自相关话题

Python中怎么去除字符串中间的空格?

回复

编程语言采菊篱下 回复了问题 • 2 人关注 • 1 个回复 • 1431 次浏览 • 2016-08-13 14:56 • 来自相关话题

用Python从网页提取的文本,转换成str格式后,怎么逐行处理呢?

回复

编程语言采菊篱下 回复了问题 • 2 人关注 • 2 个回复 • 987 次浏览 • 2016-07-27 11:51 • 来自相关话题

Python的web框架有哪些

回复

编程语言采菊篱下 回复了问题 • 2 人关注 • 2 个回复 • 1305 次浏览 • 2015-12-22 19:00 • 来自相关话题

Python在生产环境都可以用来做什么?

回复

编程语言koyo 回复了问题 • 2 人关注 • 3 个回复 • 2318 次浏览 • 2015-12-14 14:45 • 来自相关话题

Python操作各种数据库

编程语言采菊篱下 发表了文章 • 0 个评论 • 304 次浏览 • 2017-04-27 17:54 • 来自相关话题

我们在写代码的时候,经常会操作数据库,增删改查,数据库有很多类型,关系型数据库和非关系数据库,这里咱们介绍一下python怎么操作mysql、redis和mongodb。
 

一、操作mysql

python3中操作mysql数据需要安装一个第三方模块,pymysql,使用pip install pymysql安装即可,在python2中是MySQLdb模块,在python3中没有MySQLdb模块了,所以使用pymysql。
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()
# 执行SQL,并返回收影响行数
effect_row = cursor.execute("update students set name = 'niuhy' where id = 1;")
# 执行SQL,并返回受影响行数
#effect_row = cursor.execute("update students set name = 'niuhy' where id = %s;", (1,))
# 执行SQL,并返回受影响行数
effect_row = cursor.executemany("insert into students (name,age) values (%s,%s); ", [("hangyang",18),("12345",20)])
#执行select语句
cursor.execute("select * from students;")
#获取查询结果的第一条数据,返回的是一个元组
row_1 = cursor.fetchone()
# 获取前n行数据
row_2 = cursor.fetchmany(3)
# 获取所有数据
row_3 = cursor.fetchall()
# 提交,不然无法保存新建或者修改的数据
conn.commit()
# 获取最新自增ID
new_id = cursor.lastrowid
print(new_id)
# 关闭游标
cursor.close()
# 关闭连接
conn.close()上面的操作,获取到的返回结果都是元组,如果想获取到的结果是一个字典类型的话,可以使用下面这样的操作
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()

cursor = coon.cursor(cursor=pymysql.cursors.DictCursor)#需要指定游标的类型,字典类型
# 执行SQL
cursor.execute("select * from user;")
#获取返回结果,这个时候返回结果是一个字典
res = cursor.fetchone()#返回一条数据,如果结果是多条的话
print(res)
res2 = cursor.fetchall()#所有的数据一起返回

二、操作redis

redis是一个nosql类型的数据库,数据都存在内存中,有很快的读写速度,python操作redis使用redis模块,pip安装即可
import redis
r = redis.Redis(host='127.0.0.1',port=6379,db=0)#指定连接redis的端口和ip以及哪个数据库
r.set('name', 'value')#set string类型的值
r.setnx('name2', 'value')#设置的name的值,如果name不存在的时候才会设置
r.setex('name3', 'value', 3)#设置的name的值,和超时时间,过了时间key就会自动失效
r.mset(k1='v1',k2='v2')#批量设置值
r.get('name')#获取值
print(r.mget('k1','k2'))#批量获取key

r.delete('name')#删除值
r.delete('k1','k2')#批量删除
#======下面是操作哈希类型的
r.hset('hname', 'key', 'value')#set 哈希类型的值
r.hset('hname', 'key1', 'value2')#set 哈希类型的值
r.hsetnx('hname','key2','value23')#给name为hname设置key和value,和上面的不同的是key不存在的时候
#才会set
r.hmset('hname',{'k1':'v1','k2':'v2'})#批量设置哈希类型的key和value
r.hget('name', 'key')#获取哈希类型的值
print(r.hgetall('hname'))#获取这个name里所有的key和value
r.hdel('hname','key')#删除哈希类型的name里面指定的值
print(r.keys())#获取所有的key

三、操作mongodb

mongodb和redis一样,也是一个nosql类型的数据库,它和redis的区别是,redis把整个数据都放在内存,而mongodb是把数据放在磁盘上的。 python操作mongodb使用pymongo模块,pip安装即可,操作如下:
import pymongo
conn = pymongo.MongoClient(host='211.149.218.16',port=27017)#连接mongodb
db = conn.szz#选择哪个数据库
db.authenticate('admin','123456')#如果有账号密码的话,指定账号密码
collection = db.stus#使用数据库里面哪个集合,就相当于mysql里面的表
collection.drop()#删除指定的集合,也就是删除这个表
stu={
'name':'牛牛',
'age':38,
'sex':'男'
}
stus = [
{'name':'python',
'addr':'北京',
'sex':'未知',
'age':38
},
{
'name':'mongodb',
'addr':'USA',
'money':18.01,
'age':20
}
]
collection.save(stu)#插入单条数据
collection.insert(stus)#插入单条和多条,如果是多条的话,传入的就是一个list
=====比较操作符=======
# $lt
# 小于
# $lte
# 小于等于
# $gt
# 大于
# $gte
# 大于等于
# $ne
# 不等于
$set 获取前面的结果集
collection.update({'name':'牛牛'},{'name':'niuhy','age':20})#更新数据
collection.update({'name':'牛牛'},{'$set':{'addr':'河南'}})#在原来数据的基础上修改
collection.update({'name':'牛牛'},
{'$set':{'addr':'河南'}},
multi=True)#multi参数的作用是如果有多个结果的话,是否全部修改

collection.remove({'name':'牛牛'})#删除指定的数据,如果不传入参数,删除的是全部的数据
collection.remove()#删除全部数据
data = collection.find({'name':'mongodb'})#查询指定的数据
all_data = collection.find()#不写参数就是查询所有的数据
my_data = collection.find({'age':{'$gte':18}})#查询大于18岁的
for d in my_data:#获取数据,所有查询数据都需要使用循环来获取
print(d)#每个元素都是一个字典分享转载原文:牛牛杂货铺。 查看全部
我们在写代码的时候,经常会操作数据库,增删改查,数据库有很多类型,关系型数据库和非关系数据库,这里咱们介绍一下python怎么操作mysql、redis和mongodb。
 


、操作mysql


python3中操作mysql数据需要安装一个第三方模块,pymysql,使用pip install pymysql安装即可,在python2中是MySQLdb模块,在python3中没有MySQLdb模块了,所以使用pymysql。
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()
# 执行SQL,并返回收影响行数
effect_row = cursor.execute("update students set name = 'niuhy' where id = 1;")
# 执行SQL,并返回受影响行数
#effect_row = cursor.execute("update students set name = 'niuhy' where id = %s;", (1,))
# 执行SQL,并返回受影响行数
effect_row = cursor.executemany("insert into students (name,age) values (%s,%s); ", [("hangyang",18),("12345",20)])
#执行select语句
cursor.execute("select * from students;")
#获取查询结果的第一条数据,返回的是一个元组
row_1 = cursor.fetchone()
# 获取前n行数据
row_2 = cursor.fetchmany(3)
# 获取所有数据
row_3 = cursor.fetchall()
# 提交,不然无法保存新建或者修改的数据
conn.commit()
# 获取最新自增ID
new_id = cursor.lastrowid
print(new_id)
# 关闭游标
cursor.close()
# 关闭连接
conn.close()
上面的操作,获取到的返回结果都是元组,如果想获取到的结果是一个字典类型的话,可以使用下面这样的操作
import pymysql
# 创建连接,指定数据库的ip地址,账号、密码、端口号、要操作的数据库、字符集
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='123456', db='data',charset='utf8')
# 创建游标
cursor = conn.cursor()

cursor = coon.cursor(cursor=pymysql.cursors.DictCursor)#需要指定游标的类型,字典类型
# 执行SQL
cursor.execute("select * from user;")
#获取返回结果,这个时候返回结果是一个字典
res = cursor.fetchone()#返回一条数据,如果结果是多条的话
print(res)
res2 = cursor.fetchall()#所有的数据一起返回


、操作redis


redis是一个nosql类型的数据库,数据都存在内存中,有很快的读写速度,python操作redis使用redis模块,pip安装即可
import redis
r = redis.Redis(host='127.0.0.1',port=6379,db=0)#指定连接redis的端口和ip以及哪个数据库
r.set('name', 'value')#set string类型的值
r.setnx('name2', 'value')#设置的name的值,如果name不存在的时候才会设置
r.setex('name3', 'value', 3)#设置的name的值,和超时时间,过了时间key就会自动失效
r.mset(k1='v1',k2='v2')#批量设置值
r.get('name')#获取值
print(r.mget('k1','k2'))#批量获取key

r.delete('name')#删除值
r.delete('k1','k2')#批量删除
#======下面是操作哈希类型的
r.hset('hname', 'key', 'value')#set 哈希类型的值
r.hset('hname', 'key1', 'value2')#set 哈希类型的值
r.hsetnx('hname','key2','value23')#给name为hname设置key和value,和上面的不同的是key不存在的时候
#才会set
r.hmset('hname',{'k1':'v1','k2':'v2'})#批量设置哈希类型的key和value
r.hget('name', 'key')#获取哈希类型的值
print(r.hgetall('hname'))#获取这个name里所有的key和value
r.hdel('hname','key')#删除哈希类型的name里面指定的值
print(r.keys())#获取所有的key


、操作mongodb


mongodb和redis一样,也是一个nosql类型的数据库,它和redis的区别是,redis把整个数据都放在内存,而mongodb是把数据放在磁盘上的。 python操作mongodb使用pymongo模块,pip安装即可,操作如下:
import pymongo
conn = pymongo.MongoClient(host='211.149.218.16',port=27017)#连接mongodb
db = conn.szz#选择哪个数据库
db.authenticate('admin','123456')#如果有账号密码的话,指定账号密码
collection = db.stus#使用数据库里面哪个集合,就相当于mysql里面的表
collection.drop()#删除指定的集合,也就是删除这个表
stu={
'name':'牛牛',
'age':38,
'sex':'男'
}
stus = [
{'name':'python',
'addr':'北京',
'sex':'未知',
'age':38
},
{
'name':'mongodb',
'addr':'USA',
'money':18.01,
'age':20
}
]
collection.save(stu)#插入单条数据
collection.insert(stus)#插入单条和多条,如果是多条的话,传入的就是一个list
=====比较操作符=======
# $lt
# 小于
# $lte
# 小于等于
# $gt
# 大于
# $gte
# 大于等于
# $ne
# 不等于
$set 获取前面的结果集
collection.update({'name':'牛牛'},{'name':'niuhy','age':20})#更新数据
collection.update({'name':'牛牛'},{'$set':{'addr':'河南'}})#在原来数据的基础上修改
collection.update({'name':'牛牛'},
{'$set':{'addr':'河南'}},
multi=True)#multi参数的作用是如果有多个结果的话,是否全部修改

collection.remove({'name':'牛牛'})#删除指定的数据,如果不传入参数,删除的是全部的数据
collection.remove()#删除全部数据
data = collection.find({'name':'mongodb'})#查询指定的数据
all_data = collection.find()#不写参数就是查询所有的数据
my_data = collection.find({'age':{'$gte':18}})#查询大于18岁的
for d in my_data:#获取数据,所有查询数据都需要使用循环来获取
print(d)#每个元素都是一个字典
分享转载原文:牛牛杂货铺

Python字符串反转方法小记

编程语言采菊篱下 发表了文章 • 1 个评论 • 375 次浏览 • 2017-04-09 15:29 • 来自相关话题

有个朋友开突然问我在Python下怎么把字符串倒过来排序,刚开始我懵逼了,倒过来排序有什么意义,你的场景是什么,如果你单纯问我这个作为一个小考验,我觉得搜索一大推,自行Google就好啊。他说他们需要针对密码加密,简单的逻辑就是反转加密实现,厉害了疙瘩。下面我主要记录一下Python下的几种方法。

No.1 切片方式

字符串的切片跟列表是一样的,主要是利用切片的扩展语法-1来实现def rev1(cont):
return cont[::-1]
切片详细语法查看:https://docs.python.org/2/whatsnew/2.3.html#extended-slices 

No.2 列表reverse实现

利用列表的reverse()方法这个特性,可以先将字符串转换成列表,利用reverse()方法进行反转后,再处理成字符串。def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)

No.3 内置函数reversed实现

def rev3(cont):
return ''.join(reversed(cont))

No.4 递归方法

def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]# 在Python 3里,reduce()内置函数已经被从全局名字空间里移除了,它现在被放置在fucntools模块里
from functools import reduce

def rev5(cont):
return reduce(lambda x, y : y + x, cont)

No.5 字符串拼接

def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_stringdef rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)
如上几种方法效率比较:#!/usr/bin/env python3
# Author: nock
from functools import reduce
import timeit

cont = 'kcon' * 20

def rev1(cont):
return cont[::-1]

def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)

def rev3(cont):
return ''.join(reversed(cont))

def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]

def rev5(cont):
return reduce(lambda x, y : y + x, cont)

def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_string

def rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)

if __name__ == '__main__':
print("rev1 run time is: %s" % min(timeit.repeat(lambda: rev1(cont))))
print("rev2 run time is: %s" % min(timeit.repeat(lambda: rev2(cont))))
print("rev3 run time is: %s" % min(timeit.repeat(lambda: rev3(cont))))
print("rev4 run time is: %s" % min(timeit.repeat(lambda: rev4(cont))))
print("rev5 run time is: %s" % min(timeit.repeat(lambda: rev5(cont))))
print("rev6 run time is: %s" % min(timeit.repeat(lambda: rev6(cont))))
print("rev7 run time is: %s" % min(timeit.repeat(lambda: rev7(cont))))时间结果如下:rev1 run time is: 0.45436444599181414
rev2 run time is: 2.3974227079888806
rev3 run time is: 2.633627591014374
rev4 run time is: 3.0160443240310997
rev5 run time is: 16.342944753996562
rev6 run time is: 12.666344199969899
rev7 run time is: 14.762871471000835所以如上可以看出,还是用切片的方法最好,所以记住切片步长为-1就可反转就好。 查看全部
有个朋友开突然问我在Python下怎么把字符串倒过来排序,刚开始我懵逼了,倒过来排序有什么意义,你的场景是什么,如果你单纯问我这个作为一个小考验,我觉得搜索一大推,自行Google就好啊。他说他们需要针对密码加密,简单的逻辑就是反转加密实现,厉害了疙瘩。下面我主要记录一下Python下的几种方法。


No.1 切片方式


字符串的切片跟列表是一样的,主要是利用切片的扩展语法-1来实现
def rev1(cont):
return cont[::-1]
切片详细语法查看:https://docs.python.org/2/whatsnew/2.3.html#extended-slices 


No.2 列表reverse实现


利用列表的reverse()方法这个特性,可以先将字符串转换成列表,利用reverse()方法进行反转后,再处理成字符串。
def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)


No.3 内置函数reversed实现


def rev3(cont):
return ''.join(reversed(cont))


No.4 递归方法


def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]
# 在Python 3里,reduce()内置函数已经被从全局名字空间里移除了,它现在被放置在fucntools模块里
from functools import reduce

def rev5(cont):
return reduce(lambda x, y : y + x, cont)


No.5 字符串拼接


def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_string
def rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)

如上几种方法效率比较:
#!/usr/bin/env python3
# Author: nock
from functools import reduce
import timeit

cont = 'kcon' * 20

def rev1(cont):
return cont[::-1]

def rev2(cont):
result = list(cont)
result.reverse()
return ''.join(result)

def rev3(cont):
return ''.join(reversed(cont))

def rev4(cont):
if cont == "":
return cont
else:
return rev4(cont[1:])+cont[0]

def rev5(cont):
return reduce(lambda x, y : y + x, cont)

def rev6(cont):
new_string = ''
index = len(cont)
while index:
index -= 1 # index = index - 1
new_string += cont[index] # new_string = new_string + character
return new_string

def rev7(cont):
new_strings =
index = len(cont)
while index:
index -= 1
new_strings.append(cont[index])
return ''.join(new_strings)

if __name__ == '__main__':
print("rev1 run time is: %s" % min(timeit.repeat(lambda: rev1(cont))))
print("rev2 run time is: %s" % min(timeit.repeat(lambda: rev2(cont))))
print("rev3 run time is: %s" % min(timeit.repeat(lambda: rev3(cont))))
print("rev4 run time is: %s" % min(timeit.repeat(lambda: rev4(cont))))
print("rev5 run time is: %s" % min(timeit.repeat(lambda: rev5(cont))))
print("rev6 run time is: %s" % min(timeit.repeat(lambda: rev6(cont))))
print("rev7 run time is: %s" % min(timeit.repeat(lambda: rev7(cont))))
时间结果如下:
rev1 run time is: 0.45436444599181414
rev2 run time is: 2.3974227079888806
rev3 run time is: 2.633627591014374
rev4 run time is: 3.0160443240310997
rev5 run time is: 16.342944753996562
rev6 run time is: 12.666344199969899
rev7 run time is: 14.762871471000835
所以如上可以看出,还是用切片的方法最好,所以记住切片步长为-1就可反转就好。

Python生成器解析式和Zip函数介绍

编程语言采菊篱下 发表了文章 • 0 个评论 • 342 次浏览 • 2017-03-23 17:31 • 来自相关话题

生成器解析式

对列表解析来说,只需要简单的把中括号换成小括号就可以了,生成器解析式是按需计算的或者说延迟计算的或者叫惰性求值。
 
#!/usr/bin/env python3
# Author: nock

def inc(x):
print('inc {0}'.format(x))
return x + 1

# 生成一个迭代器对象
obj = (inc(x) for x in range(10))
print(obj)

Result:
<generator object <genexpr> at 0x107d87678>#!/usr/bin/env python3
# Author: nock

# 生成一个迭代器对象
obj = (x for x in range(10))
l = [x for x in range(10)]

print(next(obj))
print(next(obj))
print(next(obj))

print(l[4])
try:
print(obj[1])
except Exception as e:
print("Exception is: {0}".format(e))
print(next(obj))Result:
0
1
2
4
Exception is: 'generator' object is not subscriptable
3生成器无下标获取。
 

Zip





zip 函数用于合并多个可迭代对象,合并后的长度等于最短的可迭代对象的长度 查看全部


生成器解析式


对列表解析来说,只需要简单的把中括号换成小括号就可以了,生成器解析式是按需计算的或者说延迟计算的或者叫惰性求值。
 
#!/usr/bin/env python3
# Author: nock

def inc(x):
print('inc {0}'.format(x))
return x + 1

# 生成一个迭代器对象
obj = (inc(x) for x in range(10))
print(obj)

Result:
<generator object <genexpr> at 0x107d87678>
#!/usr/bin/env python3
# Author: nock

# 生成一个迭代器对象
obj = (x for x in range(10))
l = [x for x in range(10)]

print(next(obj))
print(next(obj))
print(next(obj))

print(l[4])
try:
print(obj[1])
except Exception as e:
print("Exception is: {0}".format(e))
print(next(obj))
Result:
0
1
2
4
Exception is: 'generator' object is not subscriptable
3
生成器无下标获取。
 


Zip


zip.png

zip 函数用于合并多个可迭代对象,合并后的长度等于最短的可迭代对象的长度

解锁Python集合推导式和字典推导式

编程语言采菊篱下 发表了文章 • 0 个评论 • 416 次浏览 • 2017-03-19 22:23 • 来自相关话题

集合推导式

集合推导式(set comprehensions)跟列表推导式也是类似的, 唯一的区别在于它们使用大括号{}表示。Code:
sets = {x for x in range(10)}
Result:
{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}



集合解析把列表解析中的中括号变成大括号,返回集合。
 
下面我们来个应用场景,一直一个列表中有很多元素,我们做到快速去重。Code:
heavy = {x for x in [2, 3, 5, 3, 5, 2, 6]}
print(heavy)
Result:
{2, 3, 5, 6}集合推导式生成内容,结果要是可hash的:





字典推导式

字典推导式(dict comprehensions)和列表推导的使用方法也是类似的。




字典解析也是使用大括号包围,并且需要两个表达式,一个生成key, 一个生成value 两个表达式之间使用冒号分割,返回结果是字典.

说了这么多推导式,为什么没有元组推导式呢,元组和列表的操作几乎是一样的,除了不可变特性以外Code:
tuple([x for x in range(10)])
Result:
(0, 1, 2, 3, 4, 5, 6, 7, 8, 9) 查看全部


集合推导式


集合推导式(set comprehensions)跟列表推导式也是类似的, 唯一的区别在于它们使用大括号{}表示。
Code:
sets = {x for x in range(10)}
Result:
{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}
type.png

集合解析把列表解析中的中括号变成大括号,返回集合。
 
下面我们来个应用场景,一直一个列表中有很多元素,我们做到快速去重。
Code:
heavy = {x for x in [2, 3, 5, 3, 5, 2, 6]}
print(heavy)
Result:
{2, 3, 5, 6}
集合推导式生成内容,结果要是可hash的:
hashable.png


字典推导式


字典推导式(dict comprehensions)和列表推导的使用方法也是类似的。
dictreb.png

字典解析也是使用大括号包围,并且需要两个表达式,一个生成key, 一个生成value 两个表达式之间使用冒号分割,返回结果是字典.

说了这么多推导式,为什么没有元组推导式呢,元组和列表的操作几乎是一样的,除了不可变特性以外
Code:
tuple([x for x in range(10)])
Result:
(0, 1, 2, 3, 4, 5, 6, 7, 8, 9)

Python使用类来写装饰器

编程语言采菊篱下 发表了文章 • 0 个评论 • 306 次浏览 • 2017-03-19 17:37 • 来自相关话题

前两天发现了装饰器可以直接使用类来写,分享一下,需要用类里面的__call__方法,__call__方法就是可以把这个实例当成一个函数来调用,如果正常使用类里面的方法的话,实例方法要先实例化类,然后才能调用,静态方法、类方法则需要用类名或者实例化之后的对象来调用,而实例化之后的这个对象,是不能被调用的,__call__方法就是把这个实例变成一个可以调用的对象,也就是说实例化之后,这个对象就可以和一个普通函数一样被调用。

示例代码如下:
class Foo:
def __call__(self, *args, **kwargs):
print('call....')
def test(self):#
print('test....')
if __name__ == '__main__':
t = Foo()#实例化类
t.test()#正常调用实例方法
t()#直接调用实例化之后的对象运行结果:
>>>test.... #这个是调用test方法的时候输出的
>>>call....#这个是执行调用这个实例化之后的方法输出的理解了上面的之后,就可以使用class来写一个装饰器了,计算程序的运行时间,当然思想和以前用函数写装饰器是一样的
class Fuck(object):
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
import time
start_time = time.time()
res = self.func(*args, **kwargs)
end_time = time.time()
print('the function "%s" run time is %s' % (self.func.__name__,
(end_time - start_time)))
return res
@Fuck
def run(name):
import time
time.sleep(1)
return 'sb_%s' % name
print(run('hyf'))运行结果:
>>>the function "run" run time is 1.0001001358032227#这个是装饰器帮我们计算的函数运行时间
>>>sb_hyf#这个是正常运行run函数的时候,返回的值
原文地址:http://www.nnzhp.cn/blog/2017/01/16/1/  查看全部
前两天发现了装饰器可以直接使用类来写,分享一下,需要用类里面的__call__方法,__call__方法就是可以把这个实例当成一个函数来调用,如果正常使用类里面的方法的话,实例方法要先实例化类,然后才能调用,静态方法、类方法则需要用类名或者实例化之后的对象来调用,而实例化之后的这个对象,是不能被调用的,__call__方法就是把这个实例变成一个可以调用的对象,也就是说实例化之后,这个对象就可以和一个普通函数一样被调用。

示例代码如下:
class Foo:
def __call__(self, *args, **kwargs):
print('call....')
def test(self):#
print('test....')
if __name__ == '__main__':
t = Foo()#实例化类
t.test()#正常调用实例方法
t()#直接调用实例化之后的对象
运行结果:
>>>test.... #这个是调用test方法的时候输出的
>>>call....#这个是执行调用这个实例化之后的方法输出的
理解了上面的之后,就可以使用class来写一个装饰器了,计算程序的运行时间,当然思想和以前用函数写装饰器是一样的
class Fuck(object):
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
import time
start_time = time.time()
res = self.func(*args, **kwargs)
end_time = time.time()
print('the function "%s" run time is %s' % (self.func.__name__,
(end_time - start_time)))
return res
@Fuck
def run(name):
import time
time.sleep(1)
return 'sb_%s' % name
print(run('hyf'))
运行结果:
>>>the function "run" run time is 1.0001001358032227#这个是装饰器帮我们计算的函数运行时间
>>>sb_hyf#这个是正常运行run函数的时候,返回的值
原文地址:http://www.nnzhp.cn/blog/2017/01/16/1/ 

解锁Python列表推导式

编程语言采菊篱下 发表了文章 • 0 个评论 • 347 次浏览 • 2017-03-18 00:28 • 来自相关话题

Pythonic的核心就是Python之禅,而Python的列表推导式就得以很好的体现。

列表推导式

定义:
列表推导式(又称列表解析式)提供了一种简明扼要的方法来创建列表。

它的结构是在一个中括号里包含一个表达式,然后是一个for语句,然后是0个或多个for或者if语句。那个表达式可以是任意的,意思是你可以在列表中放入任意类型的对象。返回结果将是一个新的列表,在这个以if和for语句为上下文的表达式运行完成之后产生。
 
列表解析的一般形式:
[expr for item in itratorable]
Code: [2 ** n for n in range(10)]

Result: [1, 2, 4, 8, 16, 32, 64, 128, 256, 512]



列表解析返回的是列表, 列表的内容是表达式执行的结果.
 
[expr for item in iterable if cond]

[x ** 0.5 for x in range(10) if x % 2 == 0]
[0.0, 1.4142135623730951, 2.0, 2.449489742783178, 2.8284271247461903][expr for item in iterable if cond1 if cond2]

[x for x in range(10) if x % 2 == 0 if x > 1]
[2, 4, 6, 8][expr for item1 in iterable1 for item2 in iterable2]

[(x, y) for x in range(10) for y in range(10) if (x+y) %2 == 0]







列表解析用于对可迭代对象做过滤和转换,返回值是列表.
 
特性一:代码变短,可读性更好




从上图代码示例中我们明显可以看出,列表推导式相比常规方法,写出来的代码更加符合pythonic,更加简短,可读性更好。
 
有些人甚至更喜欢使用它而不是filter函数生成列表,但是当你使用列表推导式效果会更加,列表推导式在有些情况下超赞,特别是当你需要使用for循环来生成一个新列表.
 
特征二:推导式速度更快
#!/usr/bin/env python3
# author: nock
import timeit

lst = list(range(10))
# 常规方法
def origin(lst):
plus_one = []
for i in lst:
plus_one.append(i + 1)
return plus_one

# 列表推导式
def fast(lst):
return [ x + 1 for x in lst ]

otime = timeit.timeit('origin(range(10))', globals=globals())
print("func origin exec time is {0}".format(otime))

ftime = timeit.timeit('fast(range(10))', globals=globals())
print("func origin exec time is {0}".format(ftime))结果:
func origin exec time is 2.1059355960023822
func origin exec time is 1.6507169340038672
如果你使用map或者filter结合lambda生成列表,也是没有列表推导式速度快的,有兴趣的可以自己Coding一下。
  查看全部
Pythonic的核心就是Python之禅,而Python的列表推导式就得以很好的体现。


列表推导式


定义:
列表推导式(又称列表解析式)提供了一种简明扼要的方法来创建列表。

它的结构是在一个中括号里包含一个表达式,然后是一个for语句,然后是0个或多个for或者if语句。那个表达式可以是任意的,意思是你可以在列表中放入任意类型的对象。返回结果将是一个新的列表,在这个以if和for语句为上下文的表达式运行完成之后产生。
 
列表解析的一般形式:
[expr for item in itratorable]

Code: [2 ** n for n in range(10)]

Result: [1, 2, 4, 8, 16, 32, 64, 128, 256, 512]
listresult.png

列表解析返回的是列表, 列表的内容是表达式执行的结果.
 
[expr for item in iterable if cond]

[x ** 0.5 for x in range(10) if x % 2 == 0]
[0.0, 1.4142135623730951, 2.0, 2.449489742783178, 2.8284271247461903]
[expr for item in iterable if cond1 if cond2]

[x for x in range(10) if x % 2 == 0 if x > 1]
[2, 4, 6, 8]
[expr for item1 in iterable1 for item2 in iterable2]

[(x, y) for x in range(10) for y in range(10) if (x+y) %2 == 0]
listerror.png

listdie.png

列表解析用于对可迭代对象做过滤和转换,返回值是列表.
 
特性一:代码变短,可读性更好
list.png

从上图代码示例中我们明显可以看出,列表推导式相比常规方法,写出来的代码更加符合pythonic,更加简短,可读性更好。
 
有些人甚至更喜欢使用它而不是filter函数生成列表,但是当你使用列表推导式效果会更加,列表推导式在有些情况下超赞,特别是当你需要使用for循环来生成一个新列表.
 
特征二:推导式速度更快
#!/usr/bin/env python3
# author: nock
import timeit

lst = list(range(10))
# 常规方法
def origin(lst):
plus_one = []
for i in lst:
plus_one.append(i + 1)
return plus_one

# 列表推导式
def fast(lst):
return [ x + 1 for x in lst ]

otime = timeit.timeit('origin(range(10))', globals=globals())
print("func origin exec time is {0}".format(otime))

ftime = timeit.timeit('fast(range(10))', globals=globals())
print("func origin exec time is {0}".format(ftime))
结果:
func origin exec time is 2.1059355960023822
func origin exec time is 1.6507169340038672

如果你使用map或者filter结合lambda生成列表,也是没有列表推导式速度快的,有兴趣的可以自己Coding一下。
 

Python最差实践变更

编程语言chris 发表了文章 • 0 个评论 • 334 次浏览 • 2016-12-20 17:28 • 来自相关话题

最近在看一些陈年老系统,其中有一些不好的代码习惯遗留下来的坑;加上最近自己也写了一段烂代码导致服务器负载飙升,所以就趁此机会总结下我看到过/写过的自认为不好的Python代码习惯,时刻提醒自己远离这些“最差实践”,避免挖坑。

下面所举的例子中,有一部分会造成性能问题,有一部分会导致隐藏bug,或日后维护、重构困难,还有一部分纯粹是我认为不够pythonic。所以大家自行甄别,取精去糟吧。
 

函数默认参数使用可变对象​

这个例子我想大家应该在各种技术文章中见过许多遍了,也足以证明这是一个大坑。
 
先看错误示范吧:
def use_mutable_default_param(idx=0, ids=[]):
ids.append(idx)
print(idx)
print(ids)

use_mutable_default_param(idx=1)
use_mutable_default_param(idx=2)输出:
1
[1]
2
[1, 2]理解这其中的原因,最重要的是有两点:
函数本身也是一个对象,默认参数绑定于这个函数对象上append这类方法会直接修改对象,所以下次调用此函数时,其绑定的默认参数已经不再是空list了
 
正确的做法如下:
def donot_use_mutable_default_param(idx=0, ids=None):
if ids is None:
ids = []
ids.append(idx)
print(idx)
print(ids)

try…except不具体指明异常类型

虽然在Python中使用try…except不会带来严重的性能问题,但是不加区分,直接捕获所有类型异常的做法,往往会掩盖掉其他的bug,造成难以追查的bug。

一般的,我觉得应该尽量少的使用try…except,这样可以在开发期尽早的发现问题。即使要使用try…except,也应该尽可能的指定出要捕获的具体异常,并在except语句中将异常信息记入log,或者处理完之后,再直接raise出来。
 

关于dict的冗余代码

我经常能够看到这样的代码:
d = {}
datas = [1, 2, 3, 4, 2, 3, 4, 1, 5]
for k in datas:
if k not in d:
d[k] = 0
d[k] += 1其实,完全可以使用collections.defaultdict这一数据结构更简单优雅的实现这样的功能:
default_d = defaultdict(lambda: 0)
datas = [1, 2, 3, 4, 2, 3, 4, 1, 5]
for k in datas:
default_d[k] += 1 同样的,这样的代码:
# d is a dict
if 'list' not in d:
d['list'] = []
d['list'].append(x)完全可以用这样一行代码替代:
# d is a dict
d.setdefault('list', []).append(x)同样的,下面这两种写法一看就是带有浓浓的C味儿:
# d is a dict
for k in d:
v = d[k]
# do something

# l is a list
for i in len(l):
v = l[i]
# do something应该用更pythonic的写法:
# d is a dict
for k, v in d.iteritems():
# do something
pass

# l is a list
for i, v in enumerate(l):
# do something
pass另外,enumerate其实还有个第二参数,表示序号从几开始。如果想要序号从1开始数起,可以使用enumerate(l, 1)。 
 

使用flag变量而不使用for…else语句

同样,这样的代码也很常见:
search_list = ['Jone', 'Aric', 'Luise', 'Frank', 'Wey']
found = False
for s in search_list:
if s.startswith('C'):
found = True
# do something when found
print('Found')
break

if not found:
# do something when not found
print('Not found') 其实,用for…else更优雅:
search_list = ['Jone', 'Aric', 'Luise', 'Frank', 'Wey']
for s in search_list:
if s.startswith('C'):
# do something when found
print('Found')
break
else:
# do something when not found
print('Not found')

 

过度使用tuple unpacking

在Python中,允许对tuple类型进行unpack操作,如下所示:
# human = ('James', 180, 32)
name,height,age = human这个特性用起来很爽,比写name=human[0]之类的不知道高到哪里去了。所以,这一特性往往被滥用,一个human在程序的各处通过上面的方式unpack。

然而如果后来需要在human中插入一个表示性别的数据sex,那么对于所有的这种unpack都需要进行修改,即使在有些逻辑中并不会使用到性别。
# human = ('James', 180, 32)
name,height,age, _ = human
# or
# name, height, age, sex = human有如下几种方式解决这一问题:
老老实实写name=human[0]这种代码,在需要使用性别信息处加上sex=human[3]使用dict来表示human使用namedtuple
 
# human = namedtuple('human', ['name', 'height', 'age', 'sex'])
h = human('James', 180, 32, 0)
# then you can use h.name, h.sex and so on everywhere.

到处都是import *

import *是一种懒惰的行为,它不仅会污染当前的命名空间,并且还会使得pyflakes等代码检查工具失效。在后续查看代码或者debug的过程中,往往也很难从一堆import *中找到一个第三方函数的来源。

可以说这种习惯是百害而无一利的。
 

文件操作

文件操作不要使用裸奔的f = open(‘filename’)了,使用with open(‘filename’) as f来让context manager帮你处理异常情况下的关闭文件等乱七八糟的事情多好。
 

野蛮使用class.name判断类型

我曾经遇见过一个bug:为了实现某特定功能,我新写了一个class B(A),在B中重写了A的若干函数。整个实现很简单,但是就是有一部分A的功能无法生效。最后追查到的原因,就是在一些逻辑代码中,硬性的判断了entity.__class__.__name__ == ‘A’。

除非你就是想限定死继承层级中的当前类型(也就是,屏蔽未来可能会出现的子类),否则,不要使用__class__.__name__,而改用isinstance这个内建函数。毕竟,Python把这两个变量的名字都刻意带上那么多下划线,本来就是不太想让你用嘛。
 

循环内部有多层函数调用

循环内部有多层函数调用,有如下两方面的隐患:
Python没有inline函数,所以函数调用本来就会导致一定的开销,尤其是本身逻辑简单的时候,这个开销所占的比例就会挺可观的。更严重的是,在之后维护这份代码时,会容易让人忽略掉函数是在循环中被调用的,所以容易在函数内部添加了一些开销较大却不必每次循环都调用的函数,比如time.localtime()。如果是直接一个平铺直叙的循环,我想大部分的程序员都应该知道把time.localtime()写到循环的外面,但是引入多层的函数调用之后,就不一定了哦。
 
所以我建议,在循环内部,如非特别复杂的逻辑,都应该直接写在循环里,不要进行函数调用。如果一定要包装一层函数调用,应该在函数的命名或注释中,提示后续的维护者,这个函数会在循环内部使用。
 

总结

Python是一门非常容易入门的语言,严格的缩进要求和丰富的内置数据类型,使得大部分Python代码都能做到比较好的规范。但是,不严格要求自己,也很容易就写出犯二的代码。上面列出的只是很小的一部分,唯有多读、多写、多想,才能培养敏锐的代码嗅觉,第一时间发现坏味道啊。
 

分享阅读:http://blog.guoyb.com/2016/12/03/bad-py-style/
作者:yubo 查看全部
python.png
最近在看一些陈年老系统,其中有一些不好的代码习惯遗留下来的坑;加上最近自己也写了一段烂代码导致服务器负载飙升,所以就趁此机会总结下我看到过/写过的自认为不好的Python代码习惯,时刻提醒自己远离这些“最差实践”,避免挖坑。

下面所举的例子中,有一部分会造成性能问题,有一部分会导致隐藏bug,或日后维护、重构困难,还有一部分纯粹是我认为不够pythonic。所以大家自行甄别,取精去糟吧。
 


函数默认参数使用可变对象​


这个例子我想大家应该在各种技术文章中见过许多遍了,也足以证明这是一个大坑。
 
先看错误示范吧:
def use_mutable_default_param(idx=0, ids=[]):
ids.append(idx)
print(idx)
print(ids)

use_mutable_default_param(idx=1)
use_mutable_default_param(idx=2)
输出:
1
[1]
2
[1, 2]
理解这其中的原因,最重要的是有两点:
  1. 函数本身也是一个对象,默认参数绑定于这个函数对象上
  2. append这类方法会直接修改对象,所以下次调用此函数时,其绑定的默认参数已经不再是空list了

 
正确的做法如下:
def donot_use_mutable_default_param(idx=0, ids=None):
if ids is None:
ids = []
ids.append(idx)
print(idx)
print(ids)


try…except不具体指明异常类型


虽然在Python中使用try…except不会带来严重的性能问题,但是不加区分,直接捕获所有类型异常的做法,往往会掩盖掉其他的bug,造成难以追查的bug。

一般的,我觉得应该尽量少的使用try…except,这样可以在开发期尽早的发现问题。即使要使用try…except,也应该尽可能的指定出要捕获的具体异常,并在except语句中将异常信息记入log,或者处理完之后,再直接raise出来。
 


关于dict的冗余代码


我经常能够看到这样的代码:
d = {}
datas = [1, 2, 3, 4, 2, 3, 4, 1, 5]
for k in datas:
if k not in d:
d[k] = 0
d[k] += 1
其实,完全可以使用collections.defaultdict这一数据结构更简单优雅的实现这样的功能:
default_d = defaultdict(lambda: 0)
datas = [1, 2, 3, 4, 2, 3, 4, 1, 5]
for k in datas:
default_d[k] += 1
同样的,这样的代码:
# d is a dict
if 'list' not in d:
d['list'] = []
d['list'].append(x)
完全可以用这样一行代码替代:
# d is a dict
d.setdefault('list', []).append(x)
同样的,下面这两种写法一看就是带有浓浓的C味儿:
# d is a dict
for k in d:
v = d[k]
# do something

# l is a list
for i in len(l):
v = l[i]
# do something
应该用更pythonic的写法:
# d is a dict
for k, v in d.iteritems():
# do something
pass

# l is a list
for i, v in enumerate(l):
# do something
pass
另外,enumerate其实还有个第二参数,表示序号从几开始。如果想要序号从1开始数起,可以使用enumerate(l, 1)。 
 


使用flag变量而不使用for…else语句


同样,这样的代码也很常见:
search_list = ['Jone', 'Aric', 'Luise', 'Frank', 'Wey']
found = False
for s in search_list:
if s.startswith('C'):
found = True
# do something when found
print('Found')
break

if not found:
# do something when not found
print('Not found')
其实,用for…else更优雅:
search_list = ['Jone', 'Aric', 'Luise', 'Frank', 'Wey']
for s in search_list:
if s.startswith('C'):
# do something when found
print('Found')
break
else:
# do something when not found
print('Not found')

 


过度使用tuple unpacking


在Python中,允许对tuple类型进行unpack操作,如下所示:
# human = ('James', 180, 32)
name,height,age = human
这个特性用起来很爽,比写name=human[0]之类的不知道高到哪里去了。所以,这一特性往往被滥用,一个human在程序的各处通过上面的方式unpack。

然而如果后来需要在human中插入一个表示性别的数据sex,那么对于所有的这种unpack都需要进行修改,即使在有些逻辑中并不会使用到性别。
# human = ('James', 180, 32)
name,height,age, _ = human
# or
# name, height, age, sex = human
有如下几种方式解决这一问题:
  1. 老老实实写name=human[0]这种代码,在需要使用性别信息处加上sex=human[3]
  2. 使用dict来表示human
  3. 使用namedtuple

 
# human = namedtuple('human', ['name', 'height', 'age', 'sex'])
h = human('James', 180, 32, 0)
# then you can use h.name, h.sex and so on everywhere.


到处都是import *


import *是一种懒惰的行为,它不仅会污染当前的命名空间,并且还会使得pyflakes等代码检查工具失效。在后续查看代码或者debug的过程中,往往也很难从一堆import *中找到一个第三方函数的来源。

可以说这种习惯是百害而无一利的。
 


文件操作


文件操作不要使用裸奔的f = open(‘filename’)了,使用with open(‘filename’) as f来让context manager帮你处理异常情况下的关闭文件等乱七八糟的事情多好。
 


野蛮使用class.name判断类型


我曾经遇见过一个bug:为了实现某特定功能,我新写了一个class B(A),在B中重写了A的若干函数。整个实现很简单,但是就是有一部分A的功能无法生效。最后追查到的原因,就是在一些逻辑代码中,硬性的判断了entity.__class__.__name__ == ‘A’。

除非你就是想限定死继承层级中的当前类型(也就是,屏蔽未来可能会出现的子类),否则,不要使用__class__.__name__,而改用isinstance这个内建函数。毕竟,Python把这两个变量的名字都刻意带上那么多下划线,本来就是不太想让你用嘛。
 


循环内部有多层函数调用


循环内部有多层函数调用,有如下两方面的隐患:
  1. Python没有inline函数,所以函数调用本来就会导致一定的开销,尤其是本身逻辑简单的时候,这个开销所占的比例就会挺可观的。
  2. 更严重的是,在之后维护这份代码时,会容易让人忽略掉函数是在循环中被调用的,所以容易在函数内部添加了一些开销较大却不必每次循环都调用的函数,比如time.localtime()。如果是直接一个平铺直叙的循环,我想大部分的程序员都应该知道把time.localtime()写到循环的外面,但是引入多层的函数调用之后,就不一定了哦。

 
所以我建议,在循环内部,如非特别复杂的逻辑,都应该直接写在循环里,不要进行函数调用。如果一定要包装一层函数调用,应该在函数的命名或注释中,提示后续的维护者,这个函数会在循环内部使用。
 


总结


Python是一门非常容易入门的语言,严格的缩进要求和丰富的内置数据类型,使得大部分Python代码都能做到比较好的规范。但是,不严格要求自己,也很容易就写出犯二的代码。上面列出的只是很小的一部分,唯有多读、多写、多想,才能培养敏锐的代码嗅觉,第一时间发现坏味道啊。
 


分享阅读:http://blog.guoyb.com/2016/12/03/bad-py-style/
作者:yubo


Python调用Zabbix API实例

运维技术Nock 发表了文章 • 0 个评论 • 646 次浏览 • 2016-12-06 19:59 • 来自相关话题

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


import json
import urllib2
from urllib2 import URLError
import sys,argparse

class zabbix_api:
def __init__(self):
self.url = 'http://192.168.210.13:81/zabbix/api_jsonrpc.php' #修改URL
self.header = {"Content-Type":"application/json"}
#验证信息
def user_login(self):
data = json.dumps({
"jsonrpc": "2.0",
"method": "user.login",
"params": {
"user": "Admin", #修改用户名
"password": "zabbix" #修改密码
},
"id": 0
})

request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "\033[041m 用户认证失败,请检查 !\033[0m", e.code
else:
response = json.loads(result.read())
result.close()
#print response['result']
self.authID = response['result']
return self.authID
#主机查询
def host_get(self,hostName=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "host.get",
"params": {
"output": "extend",
"filter":{
"host":hostName
}
},
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
if hasattr(e, 'reason'):
print 'We failed to reach a server.'
print 'Reason: ', e.reason
elif hasattr(e, 'code'):
print 'The server could not fulfill the request.'
print 'Error code: ', e.code
else:
response = json.loads(result.read())
#print response
result.close()
print "主机数量: \033[31m%s\033[0m"%(len(response['result']))
for host in response['result']:
status={"0":"OK","1":"Disabled"}
available={"0":"Unknown","1":"available","2":"Unavailable"}
#print host
if len(hostName)==0:
print "HostID : %s\t HostName : %s\t Status :\033[32m%s\033[0m \t Available :\033[31m%s\033[0m"%(host['hostid'],host['name'],status[host['status']],available[host['available']])
else:
print "HostID : %s\t HostName : %s\t Status :\033[32m%s\033[0m \t Available :\033[31m%s\033[0m"%(host['hostid'],host['name'],status[host['status']],available[host['available']])
return host['hostid']
#图形查询
def graph_get(self,hostids,graphname=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "graph.get",
"params": {
"output": "extend",
"hostids": hostids,
"sortfield": "name"
},
"auth": self.user_login(),
"id":1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
if hasattr(e, 'reason'):
print 'We failed to reach a server.'
print 'Reason: ', e.reason
elif hasattr(e, 'code'):
print 'The server could not fulfill the request.'
print 'Error code: ', e.code
else:
response = json.loads(result.read())
result.close()
print "图形数量: \033[31m%s\033[0m"%(len(response['result']))
for graph in response['result']:
if len(graphname)==0:
print "graphid : %s\t graphname : %s\t width :\033[32m%s\033[0m \t height :\033[31m%s\033[0m"%(graph['graphid'],graph['name'],graph['width'],graph['height'])
else:
print "graphid : %s\t graphname : %s\t width :\033[32m%s\033[0m \t height :\033[31m%s\033[0m"%(graph['graphid'],graph['name'],graph['width'],graph['height'])
return graph['graphid']
#筛选图查询
def screen_get(self,ScreenName=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "screen.get",
"params": {
"output": "extend",
"selectScreenItems": "extend",
"filter": {
"name": ScreenName
}
},
"auth":self.user_login(),
"id":1
})

request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print 'Error as ', e
else:
response = json.loads(result.read())
result.close()
print "筛选图数量: \033[31m%s\033[0m"%(len(response['result']))
for screen in response['result']:
if len(ScreenName)==0:
print "ScreenID : %s\t ScreenName : %s\t Hsize :\033[32m%s\033[0m \t Vsize :\033[31m%s\033[0m"%(screen['screenid'],screen['name'],screen['hsize'],screen['vsize'])
else:
print "ScreenID : %s\t ScreenName : %s\t Hsize :\033[32m%s\033[0m \t Vsize :\033[31m%s\033[0m"%(screen['screenid'],screen['name'],screen['hsize'],screen['vsize'])
return screen['screenid']
#主机组查询
def hostgroup_get(self, hostgroupName=''):
data = json.dumps({
"jsonrpc":"2.0",
"method":"hostgroup.get",
"params": {
"output": "extend",
"filter": {
"name": hostgroupName
}
},
"auth":self.user_login(),
"id":1
})

request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
#print result.read()
response = json.loads(result.read())
result.close()
#print response()
for group in response['result']:
if len(hostgroupName)==0:
print "hostgroup: \033[31m%s\033[0m \tgroupid : %s" %(group['name'],group['groupid'])
else:
print "hostgroup: \033[31m%s\033[0m \tgroupid : %s" %(group['name'],group['groupid'])
self.hostgroupID = group['groupid']
return group['groupid']
#模版查询
def template_get(self,templateName=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "template.get",
"params": {
"output": "extend",
"filter": {
"name":templateName
}
},
"auth":self.user_login(),
"id":1
})

request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
#print response
for template in response['result']:
if len(templateName)==0:
print "template : \033[31m%s\033[0m\t id : %s" % (template['name'], template['templateid'])
else:
self.templateID = response['result'][0]['templateid']
print "Template Name : \033[31m%s\033[0m "%templateName
return response['result'][0]['templateid']
#主机组创建
def hostgroup_create(self,hostgroupName):
if self.hostgroup_get(hostgroupName):
print "hostgroup \033[42m%s\033[0m is exist !"%hostgroupName
sys.exit(1)
data = json.dumps({
"jsonrpc": "2.0",
"method": "hostgroup.create",
"params": {
"name": hostgroupName
},
"auth": self.user_login(),
"id": 1
})
request=urllib2.Request(self.url,data)

for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "\033[042m 添加主机组:%s\033[0m hostgroupID : %s"%(hostgroupName,response['result']['groupids'])
#筛选图添加
def screen_create(self,ScreenName,hsize,vsize):
if self.screen_get(ScreenName):
print "Screen \033[42m%s\033[0m is exist !"%ScreenName
sys.exit(1)
data = json.dumps({
"jsonrpc": "2.0",
"method": "screen.create",
"params": {
"name": ScreenName,
"hsize": hsize,
"vsize": vsize
},
"auth": self.user_login(),
"id": 1
})
request=urllib2.Request(self.url,data)

for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "\033[042m 添加筛选图:%s\033[0m ScreenName : %s"%(ScreenName,response['result']['screenids'])
#筛选图图形添加
def screen_item_create(self,screenid,resourceid,x,y):
if self.screen_item_create(resourceid):
print "resource \033[042m%s\033[0m is exist !"%resourceid
sys.exit(1)
screen_list=[]
for i in screenid.split(','):
var = {}
var['screenid'] = self.screen_get(i)
screen_list.append(var)
data = json.dumps({
"jsonrpc": "2.0",
"method": "screenitem.create",
"params": {
"screenid": screen_list,
"resourceid": resourceid,
"x": x,
"y": y
},
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])
try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "\033[042m 添加筛选图形:%s\033[0m resourceid : %s"%(resourceid,response['result']['resourceids'])
#主机创建
def host_create(self, hostip, hostgroupName, templateName):
if self.host_get(hostip):
print "\033[041m该主机已经添加!\033[0m"
sys.exit(1)

group_list=[]
template_list=[]
for i in hostgroupName.split(','):
var = {}
var['groupid'] = self.hostgroup_get(i)
group_list.append(var)
for i in templateName.split(','):
var={}
var['templateid']=self.template_get(i)
template_list.append(var)

data = json.dumps({
"jsonrpc":"2.0",
"method":"host.create",
"params":{
"host": hostip,
"interfaces": [
{
"type": 1,
"main": 1,
"useip": 1,
"ip": hostip,
"dns": "",
"port": "10050"
}
],
"groups": group_list,
"templates": template_list,
},
"auth": self.user_login(),
"id":1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "添加主机 : \033[42m%s\031[0m \tid :\033[31m%s\033[0m" % (hostip, response['result']['hostids'])
#关闭主机
def host_disable(self,hostip):
data=json.dumps({
"jsonrpc": "2.0",
"method": "host.update",
"params": {
"hostid": self.host_get(hostip),
"status": 1
},
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])
try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print '----主机现在状态------------'
print self.host_get(hostip)
#删除主机
def host_delete(self,hostid):
hostid_list=[]
#print type(hostid)
for i in hostid.split(','):
var = {}
var['hostid'] = self.host_get(i)
hostid_list.append(var)
data=json.dumps({
"jsonrpc": "2.0",
"method": "host.delete",
"params": hostid_list,
"auth": self.user_login(),
"id": 1
})

request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except Exception,e:
print e
else:

result.close()
print "主机 \033[041m %s\033[0m 已经删除 !"%hostid
#删除筛选图
def screen_delete(self,screenid):
screenid_list=[]
for i in screenid.split(','):
var = {}
var['screenid'] = self.screen_get(i)
screenid_list.append(var)
data=json.dumps({
"jsonrpc": "2.0",
"method": "screen.delete",
"params": screenid_list,
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])
try:
result = urllib2.urlopen(request)
except Exception,e:
print e
else:
result.close()
print "筛选图 \033[041m %s\033[0m 已经删除 !"%screenid


if __name__ == "__main__":
zabbix=zabbix_api()
parser=argparse.ArgumentParser(description='zabbix api ',usage='%(prog)s [options]')
parser.add_argument('-H','--host',nargs='?',dest='listhost',default='host',help='查询主机')
parser.add_argument('-Z','--graph',nargs='?',dest='listgraph',default='graph',help='查询图形')
parser.add_argument('-G','--group',nargs='?',dest='listgroup',default='group',help='查询主机组')
parser.add_argument('-T','--template',nargs='?',dest='listtemp',default='template',help='查询模板信息')
parser.add_argument('-S','--screen',nargs='?',dest='listscreen',default='screen',help='查询筛选图')
parser.add_argument('-A','--add-group',nargs=1,dest='addgroup',help='添加主机组')
parser.add_argument('-C','--add-host',dest='addhost',nargs=3,metavar=('192.168.2.1', 'test01,test02', 'Template01,Template02'),help='添加主机,多个主机组或模板使用分号')
parser.add_argument('-B','--create-screenitem',dest='addscreenitem',nargs=4,metavar=('38', '365', '0', '0'),help='添加筛选图图形')
parser.add_argument('-J','--add-screen',nargs=3,dest='addscreen',help='添加筛选图')
parser.add_argument('-d','--disable',dest='disablehost',nargs=1,metavar=('192.168.2.1'),help='禁用主机')
parser.add_argument('-D','--delete',dest='deletehost',nargs='+',metavar=('192.168.2.1'),help='删除主机,多个主机之间用分号')
parser.add_argument('-P','--delete-screen',dest='deletescreen',nargs='+',metavar=('38'),help='删除筛选图,多个筛选图之间用分号')
parser.add_argument('-v','--version', action='version', version='%(prog)s 1.0')
if len(sys.argv)==1:
print parser.print_help()
else:
args=parser.parse_args()

if args.listhost != 'host' :
if args.listhost:
zabbix.host_get(args.listhost)
else:
zabbix.host_get()
if args.listgraph != 'graph':
if args.listgraph:
zabbix.graph_get(args.listgraph)
else:
zabbix.graph_get()
if args.listgroup !='group':
if args.listgroup:
zabbix.hostgroup_get(args.listgroup)
else:
zabbix.hostgroup_get()
if args.listtemp != 'template':
if args.listtemp:
zabbix.template_get(args.listtemp)
else:
zabbix.template_get()
if args.listscreen != 'screen':
if args.listscreen:
zabbix.screen_get(args.listscreen)
else:
zabbix.screen_get()
if args.addgroup:
zabbix.hostgroup_create(args.addgroup[0])
if args.addhost:
zabbix.host_create(args.addhost[0], args.addhost[1], args.addhost[2])
if args.addscreen:
zabbix.screen_create(args.addscreen[0],args.addscreen[1],args.addscreen[2])
if args.addscreenitem:
zabbix.screen_item_create(args.addscreenitem[0],args.addscreenitem[1],args.addscreenitem[2],args.addscreenitem[3])
if args.disablehost:
zabbix.host_disable(args.disablehost)
if args.deletehost:
zabbix.host_delete(args.deletehost[0])
if args.deletescreen:
zabbix.screen_delete(args.deletescreen[0]) 查看全部
#!/usr/bin/python 
#coding:utf-8


import json
import urllib2
from urllib2 import URLError
import sys,argparse

class zabbix_api:
def __init__(self):
self.url = 'http://192.168.210.13:81/zabbix/api_jsonrpc.php' #修改URL
self.header = {"Content-Type":"application/json"}
#验证信息
def user_login(self):
data = json.dumps({
"jsonrpc": "2.0",
"method": "user.login",
"params": {
"user": "Admin", #修改用户名
"password": "zabbix" #修改密码
},
"id": 0
})

request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "\033[041m 用户认证失败,请检查 !\033[0m", e.code
else:
response = json.loads(result.read())
result.close()
#print response['result']
self.authID = response['result']
return self.authID
#主机查询
def host_get(self,hostName=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "host.get",
"params": {
"output": "extend",
"filter":{
"host":hostName
}
},
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
if hasattr(e, 'reason'):
print 'We failed to reach a server.'
print 'Reason: ', e.reason
elif hasattr(e, 'code'):
print 'The server could not fulfill the request.'
print 'Error code: ', e.code
else:
response = json.loads(result.read())
#print response
result.close()
print "主机数量: \033[31m%s\033[0m"%(len(response['result']))
for host in response['result']:
status={"0":"OK","1":"Disabled"}
available={"0":"Unknown","1":"available","2":"Unavailable"}
#print host
if len(hostName)==0:
print "HostID : %s\t HostName : %s\t Status :\033[32m%s\033[0m \t Available :\033[31m%s\033[0m"%(host['hostid'],host['name'],status[host['status']],available[host['available']])
else:
print "HostID : %s\t HostName : %s\t Status :\033[32m%s\033[0m \t Available :\033[31m%s\033[0m"%(host['hostid'],host['name'],status[host['status']],available[host['available']])
return host['hostid']
#图形查询
def graph_get(self,hostids,graphname=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "graph.get",
"params": {
"output": "extend",
"hostids": hostids,
"sortfield": "name"
},
"auth": self.user_login(),
"id":1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
if hasattr(e, 'reason'):
print 'We failed to reach a server.'
print 'Reason: ', e.reason
elif hasattr(e, 'code'):
print 'The server could not fulfill the request.'
print 'Error code: ', e.code
else:
response = json.loads(result.read())
result.close()
print "图形数量: \033[31m%s\033[0m"%(len(response['result']))
for graph in response['result']:
if len(graphname)==0:
print "graphid : %s\t graphname : %s\t width :\033[32m%s\033[0m \t height :\033[31m%s\033[0m"%(graph['graphid'],graph['name'],graph['width'],graph['height'])
else:
print "graphid : %s\t graphname : %s\t width :\033[32m%s\033[0m \t height :\033[31m%s\033[0m"%(graph['graphid'],graph['name'],graph['width'],graph['height'])
return graph['graphid']
#筛选图查询
def screen_get(self,ScreenName=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "screen.get",
"params": {
"output": "extend",
"selectScreenItems": "extend",
"filter": {
"name": ScreenName
}
},
"auth":self.user_login(),
"id":1
})

request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print 'Error as ', e
else:
response = json.loads(result.read())
result.close()
print "筛选图数量: \033[31m%s\033[0m"%(len(response['result']))
for screen in response['result']:
if len(ScreenName)==0:
print "ScreenID : %s\t ScreenName : %s\t Hsize :\033[32m%s\033[0m \t Vsize :\033[31m%s\033[0m"%(screen['screenid'],screen['name'],screen['hsize'],screen['vsize'])
else:
print "ScreenID : %s\t ScreenName : %s\t Hsize :\033[32m%s\033[0m \t Vsize :\033[31m%s\033[0m"%(screen['screenid'],screen['name'],screen['hsize'],screen['vsize'])
return screen['screenid']
#主机组查询
def hostgroup_get(self, hostgroupName=''):
data = json.dumps({
"jsonrpc":"2.0",
"method":"hostgroup.get",
"params": {
"output": "extend",
"filter": {
"name": hostgroupName
}
},
"auth":self.user_login(),
"id":1
})

request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
#print result.read()
response = json.loads(result.read())
result.close()
#print response()
for group in response['result']:
if len(hostgroupName)==0:
print "hostgroup: \033[31m%s\033[0m \tgroupid : %s" %(group['name'],group['groupid'])
else:
print "hostgroup: \033[31m%s\033[0m \tgroupid : %s" %(group['name'],group['groupid'])
self.hostgroupID = group['groupid']
return group['groupid']
#模版查询
def template_get(self,templateName=''):
data = json.dumps({
"jsonrpc": "2.0",
"method": "template.get",
"params": {
"output": "extend",
"filter": {
"name":templateName
}
},
"auth":self.user_login(),
"id":1
})

request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
#print response
for template in response['result']:
if len(templateName)==0:
print "template : \033[31m%s\033[0m\t id : %s" % (template['name'], template['templateid'])
else:
self.templateID = response['result'][0]['templateid']
print "Template Name : \033[31m%s\033[0m "%templateName
return response['result'][0]['templateid']
#主机组创建
def hostgroup_create(self,hostgroupName):
if self.hostgroup_get(hostgroupName):
print "hostgroup \033[42m%s\033[0m is exist !"%hostgroupName
sys.exit(1)
data = json.dumps({
"jsonrpc": "2.0",
"method": "hostgroup.create",
"params": {
"name": hostgroupName
},
"auth": self.user_login(),
"id": 1
})
request=urllib2.Request(self.url,data)

for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "\033[042m 添加主机组:%s\033[0m hostgroupID : %s"%(hostgroupName,response['result']['groupids'])
#筛选图添加
def screen_create(self,ScreenName,hsize,vsize):
if self.screen_get(ScreenName):
print "Screen \033[42m%s\033[0m is exist !"%ScreenName
sys.exit(1)
data = json.dumps({
"jsonrpc": "2.0",
"method": "screen.create",
"params": {
"name": ScreenName,
"hsize": hsize,
"vsize": vsize
},
"auth": self.user_login(),
"id": 1
})
request=urllib2.Request(self.url,data)

for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "\033[042m 添加筛选图:%s\033[0m ScreenName : %s"%(ScreenName,response['result']['screenids'])
#筛选图图形添加
def screen_item_create(self,screenid,resourceid,x,y):
if self.screen_item_create(resourceid):
print "resource \033[042m%s\033[0m is exist !"%resourceid
sys.exit(1)
screen_list=[]
for i in screenid.split(','):
var = {}
var['screenid'] = self.screen_get(i)
screen_list.append(var)
data = json.dumps({
"jsonrpc": "2.0",
"method": "screenitem.create",
"params": {
"screenid": screen_list,
"resourceid": resourceid,
"x": x,
"y": y
},
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])
try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "\033[042m 添加筛选图形:%s\033[0m resourceid : %s"%(resourceid,response['result']['resourceids'])
#主机创建
def host_create(self, hostip, hostgroupName, templateName):
if self.host_get(hostip):
print "\033[041m该主机已经添加!\033[0m"
sys.exit(1)

group_list=[]
template_list=[]
for i in hostgroupName.split(','):
var = {}
var['groupid'] = self.hostgroup_get(i)
group_list.append(var)
for i in templateName.split(','):
var={}
var['templateid']=self.template_get(i)
template_list.append(var)

data = json.dumps({
"jsonrpc":"2.0",
"method":"host.create",
"params":{
"host": hostip,
"interfaces": [
{
"type": 1,
"main": 1,
"useip": 1,
"ip": hostip,
"dns": "",
"port": "10050"
}
],
"groups": group_list,
"templates": template_list,
},
"auth": self.user_login(),
"id":1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print "添加主机 : \033[42m%s\031[0m \tid :\033[31m%s\033[0m" % (hostip, response['result']['hostids'])
#关闭主机
def host_disable(self,hostip):
data=json.dumps({
"jsonrpc": "2.0",
"method": "host.update",
"params": {
"hostid": self.host_get(hostip),
"status": 1
},
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])
try:
result = urllib2.urlopen(request)
except URLError as e:
print "Error as ", e
else:
response = json.loads(result.read())
result.close()
print '----主机现在状态------------'
print self.host_get(hostip)
#删除主机
def host_delete(self,hostid):
hostid_list=[]
#print type(hostid)
for i in hostid.split(','):
var = {}
var['hostid'] = self.host_get(i)
hostid_list.append(var)
data=json.dumps({
"jsonrpc": "2.0",
"method": "host.delete",
"params": hostid_list,
"auth": self.user_login(),
"id": 1
})

request = urllib2.Request(self.url,data)
for key in self.header:
request.add_header(key, self.header[key])

try:
result = urllib2.urlopen(request)
except Exception,e:
print e
else:

result.close()
print "主机 \033[041m %s\033[0m 已经删除 !"%hostid
#删除筛选图
def screen_delete(self,screenid):
screenid_list=[]
for i in screenid.split(','):
var = {}
var['screenid'] = self.screen_get(i)
screenid_list.append(var)
data=json.dumps({
"jsonrpc": "2.0",
"method": "screen.delete",
"params": screenid_list,
"auth": self.user_login(),
"id": 1
})
request = urllib2.Request(self.url, data)
for key in self.header:
request.add_header(key, self.header[key])
try:
result = urllib2.urlopen(request)
except Exception,e:
print e
else:
result.close()
print "筛选图 \033[041m %s\033[0m 已经删除 !"%screenid


if __name__ == "__main__":
zabbix=zabbix_api()
parser=argparse.ArgumentParser(description='zabbix api ',usage='%(prog)s [options]')
parser.add_argument('-H','--host',nargs='?',dest='listhost',default='host',help='查询主机')
parser.add_argument('-Z','--graph',nargs='?',dest='listgraph',default='graph',help='查询图形')
parser.add_argument('-G','--group',nargs='?',dest='listgroup',default='group',help='查询主机组')
parser.add_argument('-T','--template',nargs='?',dest='listtemp',default='template',help='查询模板信息')
parser.add_argument('-S','--screen',nargs='?',dest='listscreen',default='screen',help='查询筛选图')
parser.add_argument('-A','--add-group',nargs=1,dest='addgroup',help='添加主机组')
parser.add_argument('-C','--add-host',dest='addhost',nargs=3,metavar=('192.168.2.1', 'test01,test02', 'Template01,Template02'),help='添加主机,多个主机组或模板使用分号')
parser.add_argument('-B','--create-screenitem',dest='addscreenitem',nargs=4,metavar=('38', '365', '0', '0'),help='添加筛选图图形')
parser.add_argument('-J','--add-screen',nargs=3,dest='addscreen',help='添加筛选图')
parser.add_argument('-d','--disable',dest='disablehost',nargs=1,metavar=('192.168.2.1'),help='禁用主机')
parser.add_argument('-D','--delete',dest='deletehost',nargs='+',metavar=('192.168.2.1'),help='删除主机,多个主机之间用分号')
parser.add_argument('-P','--delete-screen',dest='deletescreen',nargs='+',metavar=('38'),help='删除筛选图,多个筛选图之间用分号')
parser.add_argument('-v','--version', action='version', version='%(prog)s 1.0')
if len(sys.argv)==1:
print parser.print_help()
else:
args=parser.parse_args()

if args.listhost != 'host' :
if args.listhost:
zabbix.host_get(args.listhost)
else:
zabbix.host_get()
if args.listgraph != 'graph':
if args.listgraph:
zabbix.graph_get(args.listgraph)
else:
zabbix.graph_get()
if args.listgroup !='group':
if args.listgroup:
zabbix.hostgroup_get(args.listgroup)
else:
zabbix.hostgroup_get()
if args.listtemp != 'template':
if args.listtemp:
zabbix.template_get(args.listtemp)
else:
zabbix.template_get()
if args.listscreen != 'screen':
if args.listscreen:
zabbix.screen_get(args.listscreen)
else:
zabbix.screen_get()
if args.addgroup:
zabbix.hostgroup_create(args.addgroup[0])
if args.addhost:
zabbix.host_create(args.addhost[0], args.addhost[1], args.addhost[2])
if args.addscreen:
zabbix.screen_create(args.addscreen[0],args.addscreen[1],args.addscreen[2])
if args.addscreenitem:
zabbix.screen_item_create(args.addscreenitem[0],args.addscreenitem[1],args.addscreenitem[2],args.addscreenitem[3])
if args.disablehost:
zabbix.host_disable(args.disablehost)
if args.deletehost:
zabbix.host_delete(args.deletehost[0])
if args.deletescreen:
zabbix.screen_delete(args.deletescreen[0])

Python的数据序列化「Json & Pickle」

大数据/云计算采菊篱下 发表了文章 • 0 个评论 • 810 次浏览 • 2016-10-20 00:06 • 来自相关话题

在介绍Python的数据序列化模块「Json & Pickle」之前,我们先来看看为什么需要数据序列化,什么是数据序列化。
 
为什么需要数据序列化,我认为有如下两种原因:
一个原因是将对象(一切皆对象)的状态保持在存储媒介(硬盘、网盘......)中,以便可以在以后重新创建精确的副本,相当于镜像的概念,比如我们平时利用VMware虚拟机中的挂起功能,这个挂起功能就是利用数据的序列化,把虚拟机当前的状态序列化保存在本地磁盘的文件中,然后恢复的时候只需反序列化,把状态恢复即可。
 
另一个原因是通过值将对象从一个应用程序域发送到另一个应用程序域中。例如,你利用Python监控采集程序采集到的数据想传送给Zabbix处理。当两个进程在进行远程通信时,彼此可以发送各种类型的数据。无论是何种类型的数据,都会以二进制序列的形式在网络上传送。发送方需要把这个对象转换为字节序列,才能在网络上传送;接收方则需要把字节序列再恢复为对象。
 
序列化和反序列化:
序列化: 将数据结构或对象转换成二进制串的过程。反序列化:将在序列化过程中所生成的二进制串转换成数据结构或者对象的过程。

序列化的目的就是为了跨进程传递格式化数据和保存某个时刻的状态。
 
什么是数据序列化:
数据序列化就是将对象或者数据结构转化成特定的格式,使其可在网络中传输,或者可存储在内存或者文件中。反序列化则是相反的操作,将对象从序列化数据中还原出来。而对象序列化后的数据格式可以是二进制,可以是XML,也可以是JSON等任何格式。对象/数据序列化的重点在于数据的交换和传输,例如在远程调用技术(如EJB,XML-RPC, Web Service),或者在GUI控件开发(JavaBean)等等。
 
清楚了数据格式化的必要和简单认识了什么是数据格式化之后,我们就来看看Python中两个数据格式化模块的使用。
 

Json Module

Json:用于字符串和 python数据类型间进行转换;
Json模块提供了四个功能:dumps、dump、loads、load
dumps把数据类型转换成字符串 dump把数据类型转换成字符串并存储在文件中 loads把字符串转换成数据类型  load把文件打开从字符串转换成数据类型
实例如下:
#!/usr/bin/env python3
# _*_coding:utf-8_*_
# Author: Lucky.chen

import json

info = {'1MinLoad': 5, 'MemUse': '5G', 'DiskUse': '80G'}

print('dumps 操作之前数据类型: %s' % type(info))
JsonInfo = json.dumps(info)
print(JsonInfo)
# dumps 将数据通过特殊的形式转换为所有程序语言都识别的字符串
print('dumps 操作之后数据类型: %s' % type(JsonInfo))

# loads 将字符串通过特殊的形式转为python是数据类型 (将字符串转为字典)
NewInfo = json.loads(JsonInfo)
print('loads 操作之后数据类型为: %s' % type(NewInfo))

print('分割线'.center(50, '-'))

# dump 将数据通过特殊的形式转换为所有语言都识别的字符串并写入文件
with open('SystemInfo.txt', 'w') as f:
json.dump(info, f)
print('dump file end!!')

# load 从文件读取字符串并转换为python的数据类型
with open('SystemInfo.txt', 'r') as f:
LoadInfo = json.load(f)
print('load file end, data type is %s' % type(LoadInfo), LoadInfo)结果如下:
dumps 操作之前数据类型: <class 'dict'>
{"MemUse": "5G", "DiskUse": "80G", "1MinLoad": 5}
dumps 操作之后数据类型: <class 'str'>
loads 操作之后数据类型为: <class 'dict'>
-----------------------分割线------------------------
dump file end!!
load file end, data type is <class 'dict'> {'MemUse': '5G', '1MinLoad': 5, 'DiskUse': '80G'}一个错误案例如下:
#!/usr/bin/env python3
# _*_coding:utf-8_*_
# Author: Lucky.chen

import json


def test():
print('Test Func')

info = {'Name': 'crh', 'age': 18, 'Func': test}

json.dumps(info)结果:
raise TypeError(repr(o) + " is not JSON serializable")
TypeError: <function test at 0x108e7a0d0> is not JSON serializable如上可知函数不能被json序列化。
 

Pickle Module

pickle,用于python特有的类型 和 python的数据类型间进行转换
Pickle模块同样提供了四个功能:dumps、dump、loads、load
dumps把数据类型转换成字符串 dump把数据类型转换成字符串并存储在文件中 loads把字符串转换成数据类型  load把文件打开从字符串转换成数据类型

Pickle可以序列化一些较复杂的数据,和json的区别在于pickle序列化的时候,存放的是二进制的文件,所以打开一个文件的时候,我们要以二进制的格式打开。
 实例如下:
#!/usr/bin/env python3
# _*_coding:utf-8_*_
# Author: Lucky.chen

import pickle


def test(name):
print('%s write Test Func' % name)

info = {'Name': 'crh', 'age': 18, 'Func': test}

print('dumps 之前数据的类型为: %s' % type(info))

# pickle.dumps 将数据通过特殊的形式转换为只有python语言认识bytes类型(Python2.*中是字符串类型)
NewInfo = pickle.dumps(info)
print('dumps result is %s, data type is %s' % (NewInfo, type(NewInfo)))

# pickle.loads 将bytes通过特殊的形式转为python是数据类型
LoadInfo = pickle.loads(NewInfo)
print('loads result is %s, data type is %s' % (LoadInfo, type(LoadInfo)))
LoadInfo['Func']('crh')

print('分割线'.center(50, '-'))

# pickle.dump 将数据通过特殊的形式转换为只有python语言认识的字符串,并写入文件
with open('pickle.rb', 'wb') as f:
pickle.dump(info, f)

# pickle.load 从文件读取只有python语言认识的字符串并转换为python的数据类型
with open('pickle.rb', 'rb') as f:
Info = pickle.load(f)

print(Info, 'type is %s' % type(Info))结果如下:
dumps 之前数据的类型为: <class 'dict'>
dumps result is b'\x80\x03}q\x00(X\x03\x00\x00\x00ageq\x01K\x12X\x04\x00\x00\x00Nameq\x02X\x03\x00\x00\x00crhq\x03X\x04\x00\x00\x00Funcq\x04c__main__\ntest\nq\x05u.', data type is <class 'bytes'>
loads result is {'age': 18, 'Name': 'crh', 'Func': <function test at 0x1032f10d0>}, data type is <class 'dict'>
crh write Test Func
-----------------------分割线------------------------
{'age': 18, 'Name': 'crh', 'Func': <function test at 0x1032f10d0>} type is <class 'dict'>
 

总结

很多情况下不同的程序之间传送数据我们一般通过文件的方式,但是这个方法是最原始的,而dumps可以直接让数据格式化传送给对方,但是不是所有的程序都是python的,所以只利用pickle是不现实的,比如一个python的程序需要发送一段数据给一个java程序开发的应用,这时候很多内存数据的交换,就得用json了。
 
并且josn能dump的结果更可读,那么有人就问了,那还用pickle做什么不直接用josn,是这样的josn只能把常用的数据类型序列化(列表、字典、列表、字符串、数字、),比如日期格式、类对象!josn就不行了。
 
为什么他不能序列化上面的东西呢?因为josn是跨语言的!注定了它只能规范出一些通用的数据类型的格式,统一标准。
  查看全部
jason.jpg
在介绍Python的数据序列化模块「Json & Pickle」之前,我们先来看看为什么需要数据序列化,什么是数据序列化。
 
为什么需要数据序列化,我认为有如下两种原因:
一个原因是将对象(一切皆对象)的状态保持在存储媒介(硬盘、网盘......)中,以便可以在以后重新创建精确的副本,相当于镜像的概念,比如我们平时利用VMware虚拟机中的挂起功能,这个挂起功能就是利用数据的序列化,把虚拟机当前的状态序列化保存在本地磁盘的文件中,然后恢复的时候只需反序列化,把状态恢复即可。
 
另一个原因是通过值将对象从一个应用程序域发送到另一个应用程序域中。例如,你利用Python监控采集程序采集到的数据想传送给Zabbix处理。当两个进程在进行远程通信时,彼此可以发送各种类型的数据。无论是何种类型的数据,都会以二进制序列的形式在网络上传送。发送方需要把这个对象转换为字节序列,才能在网络上传送;接收方则需要把字节序列再恢复为对象。
 
序列化和反序列化:
  • 序列化: 将数据结构或对象转换成二进制串的过程。
  • 反序列化:将在序列化过程中所生成的二进制串转换成数据结构或者对象的过程。


序列化的目的就是为了跨进程传递格式化数据和保存某个时刻的状态。
 
什么是数据序列化:
数据序列化就是将对象或者数据结构转化成特定的格式,使其可在网络中传输,或者可存储在内存或者文件中。反序列化则是相反的操作,将对象从序列化数据中还原出来。而对象序列化后的数据格式可以是二进制,可以是XML,也可以是JSON等任何格式。对象/数据序列化的重点在于数据的交换和传输,例如在远程调用技术(如EJB,XML-RPC, Web Service),或者在GUI控件开发(JavaBean)等等。
 
清楚了数据格式化的必要和简单认识了什么是数据格式化之后,我们就来看看Python中两个数据格式化模块的使用。
 


Json Module


Json:用于字符串和 python数据类型间进行转换;
Json模块提供了四个功能:dumps、dump、loads、load
  1. dumps把数据类型转换成字符串 
  2. dump把数据类型转换成字符串并存储在文件中 
  3. loads把字符串转换成数据类型  
  4. load把文件打开从字符串转换成数据类型

实例如下:
#!/usr/bin/env python3
# _*_coding:utf-8_*_
# Author: Lucky.chen

import json

info = {'1MinLoad': 5, 'MemUse': '5G', 'DiskUse': '80G'}

print('dumps 操作之前数据类型: %s' % type(info))
JsonInfo = json.dumps(info)
print(JsonInfo)
# dumps 将数据通过特殊的形式转换为所有程序语言都识别的字符串
print('dumps 操作之后数据类型: %s' % type(JsonInfo))

# loads 将字符串通过特殊的形式转为python是数据类型 (将字符串转为字典)
NewInfo = json.loads(JsonInfo)
print('loads 操作之后数据类型为: %s' % type(NewInfo))

print('分割线'.center(50, '-'))

# dump 将数据通过特殊的形式转换为所有语言都识别的字符串并写入文件
with open('SystemInfo.txt', 'w') as f:
json.dump(info, f)
print('dump file end!!')

# load 从文件读取字符串并转换为python的数据类型
with open('SystemInfo.txt', 'r') as f:
LoadInfo = json.load(f)
print('load file end, data type is %s' % type(LoadInfo), LoadInfo)
结果如下:
dumps 操作之前数据类型: <class 'dict'>
{"MemUse": "5G", "DiskUse": "80G", "1MinLoad": 5}
dumps 操作之后数据类型: <class 'str'>
loads 操作之后数据类型为: <class 'dict'>
-----------------------分割线------------------------
dump file end!!
load file end, data type is <class 'dict'> {'MemUse': '5G', '1MinLoad': 5, 'DiskUse': '80G'}
一个错误案例如下:
#!/usr/bin/env python3
# _*_coding:utf-8_*_
# Author: Lucky.chen

import json


def test():
print('Test Func')

info = {'Name': 'crh', 'age': 18, 'Func': test}

json.dumps(info)
结果:
 raise TypeError(repr(o) + " is not JSON serializable")
TypeError: <function test at 0x108e7a0d0> is not JSON serializable
如上可知函数不能被json序列化。
 


Pickle Module


pickle,用于python特有的类型 和 python的数据类型间进行转换
Pickle模块同样提供了四个功能:dumps、dump、loads、load
  1. dumps把数据类型转换成字符串 
  2. dump把数据类型转换成字符串并存储在文件中 
  3. loads把字符串转换成数据类型  
  4. load把文件打开从字符串转换成数据类型


Pickle可以序列化一些较复杂的数据,和json的区别在于pickle序列化的时候,存放的是二进制的文件,所以打开一个文件的时候,我们要以二进制的格式打开。
 实例如下:
#!/usr/bin/env python3
# _*_coding:utf-8_*_
# Author: Lucky.chen

import pickle


def test(name):
print('%s write Test Func' % name)

info = {'Name': 'crh', 'age': 18, 'Func': test}

print('dumps 之前数据的类型为: %s' % type(info))

# pickle.dumps 将数据通过特殊的形式转换为只有python语言认识bytes类型(Python2.*中是字符串类型)
NewInfo = pickle.dumps(info)
print('dumps result is %s, data type is %s' % (NewInfo, type(NewInfo)))

# pickle.loads 将bytes通过特殊的形式转为python是数据类型
LoadInfo = pickle.loads(NewInfo)
print('loads result is %s, data type is %s' % (LoadInfo, type(LoadInfo)))
LoadInfo['Func']('crh')

print('分割线'.center(50, '-'))

# pickle.dump 将数据通过特殊的形式转换为只有python语言认识的字符串,并写入文件
with open('pickle.rb', 'wb') as f:
pickle.dump(info, f)

# pickle.load 从文件读取只有python语言认识的字符串并转换为python的数据类型
with open('pickle.rb', 'rb') as f:
Info = pickle.load(f)

print(Info, 'type is %s' % type(Info))
结果如下:
dumps 之前数据的类型为: <class 'dict'>
dumps result is b'\x80\x03}q\x00(X\x03\x00\x00\x00ageq\x01K\x12X\x04\x00\x00\x00Nameq\x02X\x03\x00\x00\x00crhq\x03X\x04\x00\x00\x00Funcq\x04c__main__\ntest\nq\x05u.', data type is <class 'bytes'>
loads result is {'age': 18, 'Name': 'crh', 'Func': <function test at 0x1032f10d0>}, data type is <class 'dict'>
crh write Test Func
-----------------------分割线------------------------
{'age': 18, 'Name': 'crh', 'Func': <function test at 0x1032f10d0>} type is <class 'dict'>

 


总结


很多情况下不同的程序之间传送数据我们一般通过文件的方式,但是这个方法是最原始的,而dumps可以直接让数据格式化传送给对方,但是不是所有的程序都是python的,所以只利用pickle是不现实的,比如一个python的程序需要发送一段数据给一个java程序开发的应用,这时候很多内存数据的交换,就得用json了。
 
并且josn能dump的结果更可读,那么有人就问了,那还用pickle做什么不直接用josn,是这样的josn只能把常用的数据类型序列化(列表、字典、列表、字符串、数字、),比如日期格式、类对象!josn就不行了。
 
为什么他不能序列化上面的东西呢?因为josn是跨语言的!注定了它只能规范出一些通用的数据类型的格式,统一标准。
 

Python 备份Mysql

编程语言Not see︶ 发表了文章 • 0 个评论 • 649 次浏览 • 2016-09-23 19:26 • 来自相关话题

#!/usr/bin/env python
# Filename: mysql_backup.py
# author:kevin yang
# email:zhiwen.yang@showself.com
# date:2016-09-23
import os
import time
import sys
import datetime
from stat import *

# mysql user
User = 'root'

# mysql password
Passwd = '123456'

# mysqldump command
Mysqlcommand = 'mysqldump'

# gzip command
Gzipcommand = '/bin/gzip'

# you want backup mysql database
Mysqldata = ['PHPCMS', 'TeamToy']

# you want backup to dir
Tobackup = '/data/mysql_bak/'

for DB in Mysqldata:
# backup file name
Backfile = Tobackup + DB + '-' + time.strftime('%Y-%m-%d') + '.sql'
# gzip file name
Gzfile = Backfile +'.gz'
if os.path.isfile(Gzfile):
print Gzfile + " is already backup"
else:
# backup command
Back_command = Mysqlcommand + ' -u' + User + ' -p' + Passwd + ' -P3306 ' + DB + ' > ' + Backfile
if os.system(Back_command)==0:
print 'Successful backup to', DB + ' to ' + Backfile
else:
print 'Backup FAILED'
# gzip command
Gzip_command = Gzipcommand + ' ' + Backfile
if os.system(Gzip_command)==0:
print 'Successful Gzip to',Gzfile
else:
print 'Gzip FAILED'

# Delete back file
# show file list
filelist=[]
filelist=os.listdir(Tobackup)
# delete Gzfile 5 days ago
for i in range(len(filelist)):
ft=time.gmtime(os.stat(Tobackup+filelist[i])[ST_MTIME])
ftl=time.strftime('%Y-%m-%d',ft)
year,month,day=ftl.split('-')
ftll=datetime.datetime(int(year),int(month),int(day))
localt=time.gmtime()
localtl=time.strftime('%Y-%m-%d',localt)
year,month,day=localtl.split('-')
localtll=datetime.datetime(int(year),int(month),int(day))
days=(localtll-ftll).days
if days >5:
try:
os.remove(Tobackup+filelist[i])
print 'delete is ok'
except:
log=datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')+" remove "+Tobackup+filelist[i]+" fail \n"
print log 查看全部
#!/usr/bin/env python
# Filename: mysql_backup.py
# author:kevin yang
# email:zhiwen.yang@showself.com
# date:2016-09-23
import os
import time
import sys
import datetime
from stat import *

# mysql user
User = 'root'

# mysql password
Passwd = '123456'

# mysqldump command
Mysqlcommand = 'mysqldump'

# gzip command
Gzipcommand = '/bin/gzip'

# you want backup mysql database
Mysqldata = ['PHPCMS', 'TeamToy']

# you want backup to dir
Tobackup = '/data/mysql_bak/'

for DB in Mysqldata:
# backup file name
Backfile = Tobackup + DB + '-' + time.strftime('%Y-%m-%d') + '.sql'
# gzip file name
Gzfile = Backfile +'.gz'
if os.path.isfile(Gzfile):
print Gzfile + " is already backup"
else:
# backup command
Back_command = Mysqlcommand + ' -u' + User + ' -p' + Passwd + ' -P3306 ' + DB + ' > ' + Backfile
if os.system(Back_command)==0:
print 'Successful backup to', DB + ' to ' + Backfile
else:
print 'Backup FAILED'
# gzip command
Gzip_command = Gzipcommand + ' ' + Backfile
if os.system(Gzip_command)==0:
print 'Successful Gzip to',Gzfile
else:
print 'Gzip FAILED'

# Delete back file
# show file list
filelist=[]
filelist=os.listdir(Tobackup)
# delete Gzfile 5 days ago
for i in range(len(filelist)):
ft=time.gmtime(os.stat(Tobackup+filelist[i])[ST_MTIME])
ftl=time.strftime('%Y-%m-%d',ft)
year,month,day=ftl.split('-')
ftll=datetime.datetime(int(year),int(month),int(day))
localt=time.gmtime()
localtl=time.strftime('%Y-%m-%d',localt)
year,month,day=localtl.split('-')
localtll=datetime.datetime(int(year),int(month),int(day))
days=(localtll-ftll).days
if days >5:
try:
os.remove(Tobackup+filelist[i])
print 'delete is ok'
except:
log=datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')+" remove "+Tobackup+filelist[i]+" fail \n"
print log
Python(英语发音:/ˈpaɪθən/), 是一种面向对象、解释型计算机程序设计语言,由Guido van Rossum于1989年底发明,第一个公开发行版发行于1991年,Python 源代码同样遵循 GPL(GNU General Public License)协议 。Python语法简洁而清晰,具有丰富和强大的类库。它常被昵称为胶水语言,能够把用其他语言制作的各种模块(尤其是C/C++)很轻松地联结在一起。常见的一种应用情形是,使用Python快速生成程序的原型(有时甚至是程序的最终界面),然后对其中有特别要求的部分,用更合适的语言改写,比如3D游戏中的图形渲染模块,性能要求特别高,就可以用C/C++重写,而后封装为Python可以调用的扩展类库。需要注意的是在您使用扩展类库时可能需要考虑平台问题,某些可能不提供跨平台的实现。