python手冊

picture1213發表於2014-12-23
python例項手冊


#encoding:utf8
# 設定編碼-支援中文


0說明


手冊製作: 雪松 littlepy reboot
更新日期: 2014-10-29
歡迎系統運維加入Q群: 198173206  # 加群請回答問題
歡迎運維開發加入Q群: 365534424  # 不定期技術分享


請使用"notepad++"開啟此文件,"alt+0"將函式摺疊後方便查閱
請勿刪除資訊,轉載請說明出處,抵制不道德行為。
錯誤在所難免,還望指正!


# python例項手冊下載地址:
http://hi.baidu.com/quanzhou722/item/cf4471f8e23d3149932af2a7

# shell例項手冊最新下載地址:
http://hi.baidu.com/quanzhou722/item/f4a4f3c9eb37f02d46d5c0d9


# LazyManage運維批量管理軟體下載[shell]:
http://hi.baidu.com/quanzhou722/item/4ccf7e88a877eaccef083d1a

# LazyManage運維批量管理軟體下載[python]:
http://hi.baidu.com/quanzhou722/item/4213db3626a949fe96f88d3c


1 基礎


檢視幫助
import os
for i in dir(os):
print i         # 模組的方法
help(os.path)       # 方法的幫助


除錯
python -m trace -t aaaaaa.py

pip模組安裝

yum install python-pip            # centos安裝pip
sudo apt-get install python-pip   # ubuntu安裝pip
pip官方安裝指令碼
wget https://raw.github.com/pypa/pip/master/contrib/get-pip.py
python get-pip.py
載入環境變數
vim /etc/profile
export PATH=/usr/local/python27/bin:$PATH
. /etc/profile


pip install Package             # 安裝包 pip install requests
pip show --files Package        # 檢視安裝包時安裝了哪些檔案
pip show --files Package        # 檢視哪些包有更新
pip install --upgrade Package   # 更新一個軟體包
pip uninstall Package           # 解除安裝軟體包


變數


r=r'\n'          # 輸出時原型列印
u=u'中文'        # 定義為unicode編碼
global x         # 全域性變數
a = 0 or 2 or 1  # 布林運算賦值,a值為True既不處理後面,a值為2.  None、字串''、空元組()、空列表[],空字典{}、0、空字串都是false
name = raw_input("input:").strip()        # 輸入字串變數
num = int(raw_input("input:").strip())    # 輸入字串str轉為int型
locals()                                  # 所有區域性變數組成的字典
locals().values()                         # 所有區域性變數值的列表
os.popen("date -d @{0} +'%Y-%m-%d %H:%M:%S'".format(12)).read()    # 特殊情況引用變數 {0} 代表第一個引數


列印


# 字串 %s  整數 %d  浮點 %f  原樣列印 %r
print '字串: %s 整數: %d 浮點: %f 原樣列印: %r' % ('aa',2,1.0,'r')
print 'abc',      # 有逗號,代表不換行列印,在次列印會接著本行列印


列表


# 列表元素的個數最多 536870912
shoplist = ['apple', 'mango', 'carrot', 'banana']
shoplist[2] = 'aa'
del shoplist[0]
shoplist.insert('4','www')
shoplist.append('aaa')
shoplist[::-1]    # 倒著列印 對字元翻轉串有效
shoplist[2::3]    # 從第二個開始每隔三個列印
shoplist[:-1]     # 排除最後一個
'\t'.join(li)     # 將列表轉換成字串
sys.path[1:1]=[5] # 在位置1前面插入列表中一個值
list(set(['qwe', 'as', '123', '123']))   # 將列表通過集合去重複
eval("['1','a']")                        # 將字串當表示式求值,得到列表


元組


# 不可變
zoo = ('wolf', 'elephant', 'penguin')


字典


ab = {       'Swaroop'   : 'swaroopch@byteofpython.info',
'Larry'     : 'larry@wall.org',
}
ab['c'] = 80      # 新增字典元素
del ab['Larry']   # 刪除字典元素
ab.keys()         # 檢視所有鍵值
ab.values()       # 列印所有值
ab.has_key('a')   # 檢視鍵值是否存在
ab.items()        # 返回整個字典列表

複製字典
a = {1: {1: 2, 3: 4}}
b = a             
b[1][1] = 8888                # a和b都為 {1: {1: 8888, 3: 4}}
import copy
c = copy.deepcopy(a)          # 再次賦值 b[1][1] = 9999 拷貝字典為新的字典,互不干擾

a[2] = copy.deepcopy(a[1])    # 複製出第二個key,互不影響  {1: {1: 2, 3: 4},2: {1: 2, 3: 4}}


流程結構


if判斷


# 布林值操作符 and or not 實現多重判斷
if a == b:
print '=='
elif a < b:
print b
else:
print a
fi


while迴圈


while True:
if a == b:
print "=="
break
print "!="
else:
print 'over'

count=0
while(count<9):
print count
count += 1


for迴圈


sorted()           # 返回一個序列(列表)
zip()              # 返回一個序列(列表)
enumerate()        # 返回迴圈列表序列 for i,v in enumerate(['a','b']):
reversed()         # 反序迭代器物件
dict.iterkeys()    # 通過鍵迭代
dict.itervalues()  # 通過值迭代
dict.iteritems()   # 通過鍵-值對迭代
randline()         # 檔案迭代
iter(obj)          # 得到obj迭代器 檢查obj是不是一個序列
iter(a,b)          # 重複呼叫a,直到迭代器的下一個值等於b
for i in range(1, 5):
print i
else:
print 'over'


list = ['a','b','c','b']
for i in range(len(list)):
print list[i]
for x, Lee in enumerate(list):
print "%d %s Lee" % (x+1,Lee)

# enumerate 使用函式得到索引值和對應值
for i, v in enumerate(['tic', 'tac', 'toe']):
print(i, v)


流程結構簡寫


[ i * 2 for i in [8,-2,5]]
[16,-4,10]
[ i for i in range(8) if i %2 == 0 ]
[0,2,4,6]


tab補全


# vim /usr/lib/python2.7/dist-packages/tab.py
# python startup file
import sys
import readline
import rlcompleter
import atexit
import os
# tab completion
readline.parse_and_bind('tab: complete')
# history file
histfile = os.path.join(os.environ['HOME'], '.pythonhistory')


函式


def printMax(a, b = 1):
if a > b:
print a
return a
else:
print b
return b
x = 5
y = 7
printMax(x, y)


def update(*args,**kwargs):
p=''
for i,t in kwargs.items():
p = p+ '%s=%s,' %(i,str(t))
sql = "update  'user' set (%s) where (%s)" %(args[0],p)
print sql


update('aaa',uu='uu',id=3)


模組


# Filename: mymodule.py
def sayhi():
print 'mymodule'
version = '0.1'

# 使用模組中方法
import mymodule
from mymodule import sayhi, version
mymodule.sayhi()   # 使用模組中函式方法


類物件的方法


class Person:
# 例項化初始化的方法
def __init__(self, name ,age):
self.name = name
self.age = age
print self.name
# 有self此函式為方法
def sayHi(self):
print 'Hello, my name is', self.name
# 物件消逝的時候被呼叫
def __del__(self):
print 'over'
# 例項化物件
p = Person('Swaroop')
# 使用物件方法
p.sayHi()
# 繼承
class Teacher(Person):
def __init__(self, name, age, salary):
Person.__init__(self, name, age)
self.salary = salary
print '(Initialized Teacher: %s)' % self.name
def tell(self):
Person.tell(self)
print 'Salary: "%d"' % self.salary
t = Teacher('Mrs. Shrividya', 40, 30000)


執行模組類中的所有方法


# moniItems.py
import sys, time
import inspect


class mon:
def __init__(self, n):
self.name = n
self.data = dict()
def run(self):
print 'hello', self.name
return self.runAllGet()
def getDisk(self):
return 222
def getCpu(self):
return 111
def runAllGet(self):
for fun in inspect.getmembers(self, predicate=inspect.ismethod):
print fun[0], fun[1]
if fun[0][:3] == 'get':
self.data[fun[0][3:]] = fun[1]()
print self.data
return self.data

# 模組匯入使用
from moniItems import mon
m = mon()
m.runAllGet()


檔案處理


# 模式: 讀'r'  寫[清空整個檔案]'w' 追加[檔案需要存在]'a' 讀寫'r+' 二進位制檔案'b'  'rb','wb','rb+'


寫檔案
i={'ddd':'ccc'}
f = file('poem.txt', 'a') 
f.write("string")
f.write(str(i))
f.flush()
f.close()


讀檔案
f = file('/etc/passwd','r')
c = f.read().strip()        # 讀取為一個大字串,並去掉最後一個換行符
for i in c.spilt('\n'):     # 用換行符切割字串得到列表迴圈每行
print i
f.close()


讀檔案1
f = file('/etc/passwd','r')
while True:
line = f.readline()    # 返回一行
if len(line) == 0:
break
x = line.split(":")                  # 冒號分割定義序列
#x = [ x for x in line.split(":") ]  # 冒號分割定義序列
#x = [ x.split("/") for x in line.split(":") ]  # 先冒號分割,在/分割 列印x[6][1]
print x[6],"\n",
f.close() 

讀檔案2
f = file('/etc/passwd')
c = f.readlines()       # 讀入所有檔案內容,可反覆讀取,大檔案時佔用記憶體較大
for line in c:
print line.rstrip(),
f.close()


讀檔案3
for i in open('b.txt'):   # 直接讀取也可迭代,並有利於大檔案讀取,但不可反覆讀取
print i,

追加日誌
log = open('/home/peterli/xuesong','a')
print >> log,'faaa'
log.close()

with讀檔案
with open('a.txt') as f:
for i in f:
print i
print f.read()        # 列印所有內容為字串
print f.readlines()   # 列印所有內容按行分割的列表

csv讀配置檔案  
192.168.1.5,web # 配置檔案按逗號分割
list = csv.reader(file('a.txt'))
for line in list:
print line              #  ['192.168.1.5', 'web']


內建函式


dir(sys)            # 顯示物件的屬性
help(sys)           # 互動式幫助
int(obj)            # 轉型為整形
str(obj)            # 轉為字串
len(obj)            # 返回物件或序列長度
open(file,mode)     # 開啟檔案 #mode (r 讀,w 寫, a追加)
range(0,3)          # 返回一個整形列表
raw_input("str:")   # 等待使用者輸入
type(obj)           # 返回物件型別
abs(-22)            # 絕對值
random              # 隨機數
choice()            # 隨機返回給定序列的一個元素
divmod(x,y)         # 函式完成除法運算,返回商和餘數。
round(x[,n])        # 函式返回浮點數x的四捨五入值,如給出n值,則代表舍入到小數點後的位數
strip()             # 是去掉字串兩端多於空格,該句是去除序列中的所有字串兩端多餘的空格
del                 # 刪除列表裡面的資料
cmp(x,y)            # 比較兩個物件    #根據比較結果返回一個整數,如果x<y,則返回-1;如果x>y,則返回1,如果x==y則返回0
max()               # 字串中最大的字元
min()               # 字串中最小的字元
sorted()            # 對序列排序
reversed()          # 對序列倒序
enumerate()         # 返回索引位置和對應的值
sum()               # 總和
list()              # 變成列表可用於迭代
eval('3+4')         # 將字串當表示式求值 得到7
exec 'a=100'        # 將字串按python語句執行
exec(a+'=new')      # 將變數a的值作為新的變數
tuple()             # 變成元組可用於迭代   #一旦初始化便不能更改的資料結構,速度比list快
zip(s,t)            # 返回一個合併後的列表  s = ['11','22']  t = ['aa','bb']  [('11', 'aa'), ('22', 'bb')]
isinstance(object,int)    # 測試物件型別 int 
xrange([lower,]stop[,step])            # 函式與range()類似,但xrnage()並不建立列表,而是返回一個xrange物件


字串相關模組


string         # 字串操作相關函式和工具
re             # 正規表示式
struct         # 字串和二進位制之間的轉換
c/StringIO     # 字串緩衝物件,操作方法類似於file物件
base64         # Base16\32\64資料編解碼
codecs         # 解碼器註冊和基類
crypt          # 進行單方面加密
difflib        # 找出序列間的不同
hashlib        # 多種不同安全雜湊演算法和資訊摘要演算法的API
hma            # HMAC資訊鑑權演算法的python實現
md5            # RSA的MD5資訊摘要鑑權
rotor          # 提供多平臺的加解密服務
sha            # NIAT的安全雜湊演算法SHA
stringprep     # 提供用於IP協議的Unicode字串
textwrap       # 文字包裝和填充
unicodedate    # unicode資料庫


列表型別內建函式


list.append(obj)                 # 向列表中新增一個物件obj
list.count(obj)                  # 返回一個物件obj在列表中出現的次數
list.extend(seq)                 # 把序列seq的內容新增到列表中
list.index(obj,i=0,j=len(list))  # 返回list[k] == obj 的k值,並且k的範圍在i<=k<j;否則異常
list.insert(index.obj)           # 在索引量為index的位置插入物件obj
list.pop(index=-1)               # 刪除並返回指定位置的物件,預設是最後一個物件
list.remove(obj)                 # 從列表中刪除物件obj
list.reverse()                   # 原地翻轉列表
list.sort(func=None,key=None,reverse=False)  # 以指定的方式排序列表中成員,如果func和key引數指定,則按照指定的方式比較各個元素,如果reverse標誌被置為True,則列表以反序排列


序列型別操作符


seq[ind]              # 獲取下標為ind的元素
seq[ind1:ind2]        # 獲得下標從ind1到ind2的元素集合
seq * expr            # 序列重複expr次
seq1 + seq2           # 連線seq1和seq2
obj in seq            # 判斷obj元素是否包含在seq中
obj not in seq        # 判斷obj元素是否不包含在seq中


字串型別內建方法


string.expandtabs(tabsize=8)                  # tab符號轉為空格 #預設8個空格
string.endswith(obj,beg=0,end=len(staring))   # 檢測字串是否已obj結束,如果是返回True #如果beg或end指定檢測範圍是否已obj結束
string.count(str,beg=0,end=len(string))       # 檢測str在string裡出現次數  f.count('\n',0,len(f)) 判斷檔案行數
string.find(str,beg=0,end=len(string))        # 檢測str是否包含在string中
string.index(str,beg=0,end=len(string))       # 檢測str不在string中,會報異常
string.isalnum()                              # 如果string至少有一個字元並且所有字元都是字母或數字則返回True
string.isalpha()                              # 如果string至少有一個字元並且所有字元都是字母則返回True
string.isnumeric()                            # 如果string只包含數字字元,則返回True
string.isspace()                              # 如果string包含空格則返回True
string.isupper()                              # 字串都是大寫返回True
string.islower()                              # 字串都是小寫返回True
string.lower()                                # 轉換字串中所有大寫為小寫
string.upper()                                # 轉換字串中所有小寫為大寫
string.lstrip()                               # 去掉string左邊的空格
string.rstrip()                               # 去掉string字元末尾的空格
string.replace(str1,str2,num=string.count(str1))  # 把string中的str1替換成str2,如果num指定,則替換不超過num次
string.startswith(obj,beg=0,end=len(string))  # 檢測字串是否以obj開頭
string.zfill(width)                           # 返回字元長度為width的字元,原字串右對齊,前面填充0
string.isdigit()                              # 只包含數字返回True
string.split("分隔符")                        # 把string切片成一個列表
":".join(string.split())                      # 以:作為分隔符,將所有元素合併為一個新的字串


序列型別相關的模組


array         # 一種受限制的可變序列型別,元素必須相同型別
copy          # 提供淺拷貝和深拷貝的能力
operator      # 包含函式呼叫形式的序列操作符 operator.concat(m,n)
re            # perl風格的正規表示式查詢
StringIO      # 把長字串作為檔案來操作 如: read() \ seek()
cStringIO     # 把長字串作為檔案來操,作速度更快,但不能被繼承
textwrap      # 用作包裝/填充文字的函式,也有一個類
types         # 包含python支援的所有型別
collections   # 高效能容器資料型別


字典內建方法


dict.clear()                            # 刪除字典中所有元素
dict copy()                             # 返回字典(淺複製)的一個副本
dict.fromkeys(seq,val=None)             # 建立並返回一個新字典,以seq中的元素做該字典的鍵,val做該字典中所有鍵對的初始值
dict.get(key,default=None)              # 對字典dict中的鍵key,返回它對應的值value,如果字典中不存在此鍵,則返回default值
dict.has_key(key)                       # 如果鍵在字典中存在,則返回True 用in和not in代替
dicr.items()                            # 返回一個包含字典中鍵、值對元組的列表
dict.keys()                             # 返回一個包含字典中鍵的列表
dict.iter()                             # 方法iteritems()、iterkeys()、itervalues()與它們對應的非迭代方法一樣,不同的是它們返回一個迭代子,而不是一個列表
dict.pop(key[,default])                 # 和方法get()相似.如果字典中key鍵存在,刪除並返回dict[key]
dict.setdefault(key,default=None)       # 和set()相似,但如果字典中不存在key鍵,由dict[key]=default為它賦值
dict.update(dict2)                      # 將字典dict2的鍵值對新增到字典dict
dict.values()                           # 返回一個包含字典中所有值得列表


dict([container])     # 建立字典的工廠函式。提供容器類(container),就用其中的條目填充字典
len(mapping)          # 返回對映的長度(鍵-值對的個數)
hash(obj)             # 返回obj雜湊值,判斷某個物件是否可做一個字典的鍵值

集合方法


s.update(t)                         # 用t中的元素修改s,s現在包含s或t的成員   s |= t
s.intersection_update(t)            # s中的成員是共用屬於s和t的元素          s &= t
s.difference_update(t)              # s中的成員是屬於s但不包含在t中的元素    s -= t
s.symmetric_difference_update(t)    # s中的成員更新為那些包含在s或t中,但不是s和t共有的元素  s ^= t
s.add(obj)                          # 在集合s中新增物件obj
s.remove(obj)                       # 從集合s中刪除物件obj;如果obj不是集合s中的元素(obj not in s),將引發KeyError錯誤
s.discard(obj)                      # 如果obj是集合s中的元素,從集合s中刪除物件obj
s.pop()                             # 刪除集合s中的任意一個物件,並返回它
s.clear()                           # 刪除集合s中的所有元素
s.issubset(t)                       # 如果s是t的子集,則返回True   s <= t
s.issuperset(t)                     # 如果t是s的超集,則返回True   s >= t
s.union(t)                          # 合併操作;返回一個新集合,該集合是s和t的並集   s | t
s.intersection(t)                   # 交集操作;返回一個新集合,該集合是s和t的交集   s & t
s.difference(t)                     # 返回一個新集合,改集合是s的成員,但不是t的成員  s - t
s.symmetric_difference(t)           # 返回一個新集合,該集合是s或t的成員,但不是s和t共有的成員   s ^ t
s.copy()                            # 返回一個新集合,它是集合s的淺複製
obj in s                            # 成員測試;obj是s中的元素 返回True
obj not in s                        # 非成員測試:obj不是s中元素 返回True
s == t                              # 等價測試 是否具有相同元素
s != t                              # 不等價測試 
s < t                               # 子集測試;s!=t且s中所有元素都是t的成員
s > t                               # 超集測試;s!=t且t中所有元素都是s的成員


序列化


#!/usr/bin/python
import cPickle
obj = {'1':['4124','1241','124'],'2':['12412','142','1241']}


pkl_file = open('account.pkl','wb')
cPickle.down(obj,pkl_file)
pkl_file.close()


pkl_file = open('account.pkl','rb')
account_list = cPickle.load(pkl_file)
pkl_file.close()


檔案物件方法

file.close()                     # 關閉檔案
file.fileno()                    # 返回檔案的描述符
file.flush()                     # 重新整理檔案的內部緩衝區
file.isatty()                    # 判斷file是否是一個類tty裝置
file.next()                      # 返回檔案的下一行,或在沒有其他行時引發StopIteration異常
file.read(size=-1)               # 從檔案讀取size個位元組,當未給定size或給定負值的時候,讀取剩餘的所有位元組,然後作為字串返回
file.readline(size=-1)           # 從檔案中讀取並返回一行(包括行結束符),或返回最大size個字元
file.readlines(sizhint=0)        # 讀取檔案的所有行作為一個列表返回
file.xreadlines()                # 用於迭代,可替換readlines()的一個更高效的方法
file.seek(off, whence=0)         # 在檔案中移動檔案指標,從whence(0代表檔案起始,1代表當前位置,2代表檔案末尾)偏移off位元組
file.tell()                      # 返回當前在檔案中的位置
file.truncate(size=file.tell())  # 擷取檔案到最大size位元組,預設為當前檔案位置
file.write(str)                  # 向檔案寫入字串
file.writelines(seq)             # 向檔案寫入字串序列seq;seq應該是一個返回字串的可迭代物件


檔案物件的屬性

file.closed          # 表示檔案已被關閉,否則為False
file.encoding        # 檔案所使用的編碼  當unicode字串被寫入資料時,它將自動使用file.encoding轉換為位元組字串;若file.encoding為None時使用系統預設編碼
file.mode            # Access檔案開啟時使用的訪問模式
file.name            # 檔名
file.newlines        # 未讀取到行分隔符時為None,只有一種行分隔符時為一個字串,當檔案有多種型別的行結束符時,則為一個包含所有當前所遇到的行結束符的列表
file.softspace       # 為0表示在輸出一資料後,要加上一個空格符,1表示不加


異常處理

# try 中使用 sys.exit(2) 會被捕獲,無法退出指令碼,可使用 os._exit(2) 退出指令碼

class ShortInputException(Exception):  # 繼承Exception異常的類,定義自己的異常
def __init__(self, length, atleast):
Exception.__init__(self)
self.length = length
self.atleast = atleast
try:
s = raw_input('Enter something --> ')
if len(s) < 3:
raise ShortInputException(len(s), 3)    # 觸發異常
except EOFError:
print '\nWhy did you do an EOF on me?'
except ShortInputException, x:      # 捕捉指定錯誤資訊
print 'ShortInputException:  %d | %d' % (x.length, x.atleast)
except Exception as err:            # 捕捉所有其它錯誤資訊內容
print str(err)
#except urllib2.HTTPError as err:   # 捕捉外部匯入模組的錯誤
#except:                            # 捕捉所有其它錯誤 不會看到錯誤內容
# print 'except'
finally:                            # 無論什麼情況都會執行 關閉檔案或斷開連線等
  print 'finally' 
else:                               # 無任何異常 無法和finally同用
print 'No exception was raised.' 


不可捕獲的異常


NameError:              # 嘗試訪問一個未申明的變數
ZeroDivisionError:      # 除數為零
SyntaxErrot:            # 直譯器語法錯誤
IndexError:             # 請求的索引元素超出序列範圍
KeyError:               # 請求一個不存在的字典關鍵字
IOError:                # 輸入/輸出錯誤
AttributeError:         # 嘗試訪問未知的物件屬性
ImportError             # 沒有模組
IndentationError        # 語法縮排錯誤
KeyboardInterrupt       # ctrl+C
SyntaxError             # 程式碼語法錯誤
ValueError              # 值錯誤
TypeError               # 傳入物件型別與要求不符合


內建異常

BaseException                # 所有異常的基類
SystemExit                   # python直譯器請求退出
KeyboardInterrupt            # 使用者中斷執行
Exception                    # 常規錯誤的基類
StopIteration                # 迭代器沒有更多的值
GeneratorExit                # 生成器發生異常來通知退出
StandardError                # 所有的內建標準異常的基類
ArithmeticError              # 所有數值計算錯誤的基類
FloatingPointError           # 浮點計算錯誤
OverflowError                # 數值運算超出最大限制
AssertionError               # 斷言語句失敗
AttributeError               # 物件沒有這個屬性
EOFError                     # 沒有內建輸入,到達EOF標記
EnvironmentError             # 作業系統錯誤的基類
IOError                      # 輸入/輸出操作失敗
OSError                      # 作業系統錯誤
WindowsError                 # windows系統呼叫失敗
ImportError                  # 匯入模組/物件失敗
KeyboardInterrupt            # 使用者中斷執行(通常是ctrl+c)
LookupError                  # 無效資料查詢的基類
IndexError                   # 序列中沒有此索引(index)
KeyError                     # 對映中沒有這個鍵
MemoryError                  # 記憶體溢位錯誤(對於python直譯器不是致命的)
NameError                    # 未宣告/初始化物件(沒有屬性)
UnboundLocalError            # 訪問未初始化的本地變數
ReferenceError               # 若引用試圖訪問已經垃圾回收了的物件
RuntimeError                 # 一般的執行時錯誤
NotImplementedError          # 尚未實現的方法
SyntaxError                  # python語法錯誤
IndentationError             # 縮排錯誤
TabError                     # tab和空格混用
SystemError                  # 一般的直譯器系統錯誤
TypeError                    # 對型別無效的操作
ValueError                   # 傳入無效的引數
UnicodeError                 # Unicode相關的錯誤
UnicodeDecodeError           # Unicode解碼時的錯誤
UnicodeEncodeError           # Unicode編碼時的錯誤
UnicodeTranslateError        # Unicode轉換時錯誤
Warning                      # 警告的基類
DeprecationWarning           # 關於被棄用的特徵的警告
FutureWarning                # 關於構造將來語義會有改變的警告
OverflowWarning              # 舊的關於自動提升為長整形的警告
PendingDeprecationWarning    # 關於特性將會被廢棄的警告
RuntimeWarning               # 可疑的執行時行為的警告
SyntaxWarning                # 可疑的語法的警告
UserWarning                  # 使用者程式碼生成的警告


觸發異常


raise exclass            # 觸發異常,從exclass生成一個例項(不含任何異常引數)
raise exclass()          # 觸發異常,但現在不是類;通過函式呼叫操作符(function calloperator:"()")作用於類名生成一個新的exclass例項,同樣也沒有異常引數
raise exclass, args      # 觸發異常,但同時提供的異常引數args,可以是一個引數也可以是元組
raise exclass(args)      # 觸發異常,同上
raise exclass, args, tb  # 觸發異常,但提供一個跟蹤記錄(traceback)物件tb供使用
raise exclass,instance   # 通過例項觸發異常(通常是exclass的例項)
raise instance           # 通過例項觸發異常;異常型別是例項的型別:等價於raise instance.__class__, instance
raise string             # 觸發字串異常
raise string, srgs       # 觸發字串異常,但觸發伴隨著args
raise string,args,tb     # 觸發字串異常,但提供一個跟蹤記錄(traceback)物件tb供使用
raise                    # 重新觸發前一個異常,如果之前沒有異常,觸發TypeError


跟蹤異常棧


# traceback 獲取異常相關資料都是通過sys.exc_info()函式得到的
import traceback
import sys
try:
s = raw_input()
print int(s)
except ValueError:
# sys.exc_info() 返回值是元組,第一個exc_type是異常的物件型別,exc_value是異常的值,exc_tb是一個traceback物件,物件中包含出錯的行數、位置等資料
exc_type, exc_value, exc_tb = sys.exc_info()
print "\n%s \n %s \n %s\n" %(exc_type, exc_value, exc_tb )
traceback.print_exc()        # 列印棧跟蹤資訊

抓取全部錯誤資訊存如字典


import sys, traceback


try:
s = raw_input()
int(s)
except:
exc_type, exc_value, exc_traceback = sys.exc_info() 
traceback_details = {
'filename': exc_traceback.tb_frame.f_code.co_filename,
'lineno'  : exc_traceback.tb_lineno,
'name'    : exc_traceback.tb_frame.f_code.co_name,
'type'    : exc_type.__name__,
'message' : exc_value.message, 
}
 
del(exc_type, exc_value, exc_traceback) 
print traceback_details
f = file('test1.txt', 'a')
f.write("%s %s %s %s %s\n" %(traceback_details['filename'],traceback_details['lineno'],traceback_details['name'],traceback_details['type'],traceback_details['message'], ))
f.flush()
f.close()


除錯log


# cgitb覆蓋了預設sys.excepthook全域性異常攔截器
def func(a, b):
return a / b
if __name__ == '__main__':
import cgitb
cgitb.enable(format='text')
func(1, 0)


函數語言程式設計的內建函式


apply(func[,nkw][,kw])          # 用可選的引數來呼叫func,nkw為非關鍵字引數,kw為關鍵字引數;返回值是函式呼叫的返回值
filter(func,seq)                # 呼叫一個布林函式func來迭代遍歷每個seq中的元素;返回一個使func返回值為true的元素的序列
map(func,seq1[,seq2])           # 將函式func作用於給定序列(s)的每個元素,並用一個列表來提供返回值;如果func為None,func表現為一個身份函式,返回一個含有每個序列中元素集合的n個元組的列表
reduce(func,seq[,init])         # 將二元函式作用於seq序列的元素,每次攜帶一堆(先前的結果以及下一個序列元素),連續地將現有的結果和下一個值作用在獲得的隨後的結果上,最後減少我們的序列為一個單一的返回值;如果初始值init給定,第一個比較會是init和第一個序列元素而不是序列的頭兩個元素

# filter 即通過函式方法只保留結果為真的值組成列表
def f(x): return x % 2 != 0 and x % 3 != 0
f(3)     # 函式結果是False  3被filter拋棄
f(5)     # 函式結果是True   5被加入filter最後的列表結果
filter(f, range(2, 25))
[5, 7, 11, 13, 17, 19, 23]

# map 通過函式對列表進行處理得到新的列表
def cube(x): return x*x*x
map(cube, range(1, 11))
[1, 8, 27, 64, 125, 216, 343, 512, 729, 1000]

# reduce 通過函式會先接收初始值和序列的第一個元素,然後是返回值和下一個元素,依此類推
def add(x,y): return x+y
reduce(add, range(1, 11))      # 結果55  是1到10的和  x的值是上一次函式返回的結果,y是列表中迴圈的值


re正則


compile(pattern,flags=0)          # 對正規表示式模式pattern進行編譯,flags是可選識別符號,並返回一個regex物件
match(pattern,string,flags=0)     # 嘗試用正規表示式模式pattern匹配字串string,flags是可選識別符號,如果匹配成功,則返回一個匹配物件;否則返回None
search(pattern,string,flags=0)    # 在字串string中搜尋正規表示式模式pattern的第一次出現,flags是可選識別符號,如果匹配成功,則返回一個匹配物件;否則返回None
findall(pattern,string[,flags])   # 在字串string中搜尋正規表示式模式pattern的所有(非重複)出現:返回一個匹配物件的列表  # pattern=u'\u4e2d\u6587' 代表UNICODE
finditer(pattern,string[,flags])  # 和findall()相同,但返回的不是列表而是迭代器;對於每個匹配,該迭代器返回一個匹配物件
split(pattern,string,max=0)       # 根據正規表示式pattern中的分隔符把字元string分割為一個列表,返回成功匹配的列表,最多分割max次(預設所有)
sub(pattern,repl,string,max=0)    # 把字串string中所有匹配正規表示式pattern的地方替換成字串repl,如果max的值沒有給出,則對所有匹配的地方進行替換(subn()會返回一個表示替換次數的數值)
group(num=0)                      # 返回全部匹配物件(或指定編號是num的子組)
groups()                          # 返回一個包含全部匹配的子組的元組(如果沒匹配成功,返回一個空元組)

例子
re.findall(r'a[be]c','123abc456eaec789')         # 返回匹配物件列表 ['abc', 'aec']
re.findall("(.)12[34](..)",a)                    # 取出匹配括號中內容   a='qedqwe123dsf'
re.search("(.)123",a ).group(1)                  # 搜尋匹配的取第1個標籤
re.match("^(1|2) *(.*) *abc$", str).group(2)     # 取第二個標籤
re.match("^(1|2) *(.*) *abc$", str).groups()     # 取所有標籤
re.sub('[abc]','A','alex')                       # 替換
for i in re.finditer(r'\d+',s):                  # 迭代
print i.group(),i.span()                     #

搜尋網頁中UNICODE格式的中文
QueryAdd='http://www.anti-spam.org.cn/Rbl/Query/Result'
Ip='222.129.184.52'
s = requests.post(url=QueryAdd, data={'IP':Ip})
re.findall(u'\u4e2d\u56fd', s.text, re.S)


編碼轉換


a='中文'                    # 編碼未定義按輸入終端utf8或gbk
u=u'中文'                   # 定義為unicode編碼  u值為 u'\u4e2d\u6587'
u.encode('utf8')            # 轉為utf8格式 u值為 '\xe4\xb8\xad\xe6\x96\x87'
print u                     # 結果顯示 中文
print u.encode('utf8')      # 轉為utf8格式,當顯示終端編碼為utf8  結果顯示 中文  編碼不一致則亂碼
print u.encode('gbk')       # 當前終端為utf8 故亂碼
ord('4')                    # 字元轉ASCII碼
chr(52)                     # ASCII碼轉字元


遍歷遞迴


[os.path.join(x[0],y) for x in os.walk('/root/python/5') for y in x[2]]


for i in os.walk('/root/python/5/work/server'):
print i


2 常用模組


sys


sys.argv              # 取引數列表
sys.exit(2)           # 退出指令碼返回狀態 會被try擷取
sys.exc_info()        # 獲取當前正在處理的異常類
sys.version           # 獲取Python解釋程式的版本資訊
sys.maxint            # 最大的Int值  9223372036854775807
sys.maxunicode        # 最大的Unicode值
sys.modules           # 返回系統匯入的模組欄位,key是模組名,value是模組
sys.path              # 返回模組的搜尋路徑,初始化時使用PYTHONPATH環境變數的值
sys.platform          # 返回作業系統平臺名稱
sys.stdout            # 標準輸出
sys.stdin             # 標準輸入
sys.stderr            # 錯誤輸出
sys.exec_prefix       # 返回平臺獨立的python檔案安裝的位置
sys.stdin.readline()  # 從標準輸入讀一行
sys.stdout.write("a") # 螢幕輸出a 


os


# 相對sys模組 os模組更為底層 os._exit() try無法抓取
os.popen('id').read()      # 執行系統命令得到返回結果
os.system()                # 得到返回狀態 返回無法擷取
os.name                    # 返回系統平臺 Linux/Unix使用者是'posix'
os.getenv()                # 讀取環境變數
os.putenv()                # 設定環境變數
os.getcwd()                # 當前工作路徑
os.chdir()                 # 改變當前工作目錄
os.walk('/root/')          # 遞迴路徑

檔案處理
mkfifo()/mknod()       # 建立命名管道/建立檔案系統節點
remove()/unlink()      # 刪除檔案
rename()/renames()     # 重新命名檔案
*stat()                # 返回檔案資訊
symlink()              # 建立符號連結
utime()                # 更新時間戳
tmpfile()              # 建立並開啟('w+b')一個新的臨時檔案
walk()                 # 遍歷目錄樹下的所有檔名

目錄/資料夾
chdir()/fchdir()       # 改變當前工作目錄/通過一個檔案描述符改變當前工作目錄
chroot()               # 改變當前程式的根目錄
listdir()              # 列出指定目錄的檔案
getcwd()/getcwdu()     # 返回當前工作目錄/功能相同,但返回一個unicode物件
mkdir()/makedirs()     # 建立目錄/建立多層目錄
rmdir()/removedirs()   # 刪除目錄/刪除多層目錄

訪問/許可權
saccess()              # 檢驗許可權模式
chmod()                # 改變許可權模式
chown()/lchown()       # 改變owner和groupID功能相同,但不會跟蹤連結
umask()                # 設定預設許可權模式

檔案描述符操作
open()                 # 底層的作業系統open(對於穩健,使用標準的內建open()函式)
read()/write()         # 根據檔案描述符讀取/寫入資料 按大小讀取檔案部分內容
dup()/dup2()           # 複製檔案描述符號/功能相同,但是複製到另一個檔案描述符

裝置號
makedev()              # 從major和minor裝置號建立一個原始裝置號
major()/minor()        # 從原始裝置號獲得major/minor裝置號

os.path模組


os.path.expanduser('~/.ssh/key')   # 家目錄下檔案的全路徑


分隔
os.path.basename()         # 去掉目錄路徑,返回檔名
os.path.dirname()          # 去掉檔名,返回目錄路徑
os.path.join()             # 將分離的各部分組合成一個路徑名
os.path.spllt()            # 返回(dirname(),basename())元組
os.path.splitdrive()       # 返回(drivename,pathname)元組
os.path.splitext()         # 返回(filename,extension)元組

資訊
os.path.getatime()         # 返回最近訪問時間
os.path.getctime()         # 返回檔案建立時間
os.path.getmtime()         # 返回最近檔案修改時間
os.path.getsize()          # 返回檔案大小(位元組)

查詢
os.path.exists()          # 指定路徑(檔案或目錄)是否存在
os.path.isabs()           # 指定路徑是否為絕對路徑
os.path.isdir()           # 指定路徑是否存在且為一個目錄
os.path.isfile()          # 指定路徑是否存在且為一個檔案
os.path.islink()          # 指定路徑是否存在且為一個符號連結
os.path.ismount()         # 指定路徑是否存在且為一個掛載點
os.path.samefile()        # 兩個路徑名是否指向同一個檔案

相關模組
base64              # 提供二進位制字串和文字字串間的編碼/解碼操作
binascii            # 提供二進位制和ASCII編碼的二進位制字串間的編碼/解碼操作
bz2                 # 訪問BZ2格式的壓縮檔案
csv                 # 訪問csv檔案(逗號分隔檔案)
csv.reader(open(file))
filecmp             # 用於比較目錄和檔案
fileinput           # 提供多個文字檔案的行迭代器
getopt/optparse     # 提供了命令列引數的解析/處理
glob/fnmatch        # 提供unix樣式的萬用字元匹配的功能
gzip/zlib           # 讀寫GNU zip(gzip)檔案(壓縮需要zlib模組)
shutil              # 提供高階檔案訪問功能
c/StringIO          # 對字串物件提供類檔案介面
tarfile             # 讀寫TAR歸檔檔案,支援壓縮檔案
tempfile            # 建立一個臨時檔案
uu                  # uu格式的編碼和解碼
zipfile             # 用於讀取zip歸檔檔案的工具
environ['HOME']     # 檢視系統環境變數

子程式
os.fork()    # 建立子程式,並複製父程式所有操作  通過判斷pid = os.fork() 的pid值,分別執行父程式與子程式操作,0為子程式
os.wait()    # 等待子程式結束


跨平臺os模組屬性


linesep         # 用於在檔案中分隔行的字串
sep             # 用來分隔檔案路徑名字的字串
pathsep         # 用於分割檔案路徑的字串
curdir          # 當前工作目錄的字串名稱
pardir          # 父目錄字串名稱


commands

commands.getstatusoutput('id')       # 返回元組(狀態,標準輸出)
commands.getoutput('id')             # 只返回執行的結果, 忽略返回值
commands.getstatus('file')           # 返回ls -ld file執行的結果

檔案和目錄管理

import shutil
shutil.copyfile('data.db', 'archive.db')             # 拷貝檔案
shutil.move('/build/executables', 'installdir')      # 移動檔案或目錄


檔案萬用字元


import glob
glob.glob('*.py')    # 查詢當前目錄下py結尾的檔案


隨機模組

import random
random.choice(['apple', 'pear', 'banana'])   # 隨機取列表一個引數
random.sample(xrange(100), 10)  # 不重複抽取10個
random.random()                 # 隨機浮點數
random.randrange(6)             # 隨機整數範圍

傳送郵件


傳送郵件內容


#!/usr/bin/python
#encoding:utf8
# 匯入 smtplib 和 MIMEText 
import smtplib
from email.mime.text import MIMEText


# 定義傳送列表 
mailto_list=["272121935@qq.com","272121935@163.com"]


# 設定伺服器名稱、使用者名稱、密碼以及郵件字尾 
mail_host = "smtp.163.com"
mail_user = "mailuser"
mail_pass = "password"
mail_postfix="163.com"


# 傳送郵件函式
def send_mail(to_list, sub):
me = mail_user + "<"+mail_user+"@"+mail_postfix+">"
fp = open('context.txt')
msg = MIMEText(fp.read(),_charset="utf-8")
fp.close()
msg['Subject'] = sub
msg['From'] = me
msg['To'] = ";".join(to_list)
try:
send_smtp = smtplib.SMTP()
send_smtp.connect(mail_host)
send_smtp.login(mail_user, mail_pass)
send_smtp.sendmail(me, to_list, msg.as_string())
send_smtp.close()
return True
except Exception, e:
print str(e)
return False


if send_mail(mailto_list,"標題"):
print "測試成功"
else:
print "測試失敗"


傳送附件


#!/usr/bin/python
#encoding:utf8
import smtplib
from email.mime.multipart import MIMEMultipart
from email.mime.base import MIMEBase
from email import encoders


def send_mail(to_list, sub, filename):
me = mail_user + "<"+mail_user+"@"+mail_postfix+">"
msg = MIMEMultipart()
msg['Subject'] = sub
msg['From'] = me
msg['To'] = ";".join(to_list)
submsg = MIMEBase('application', 'x-xz')
submsg.set_payload(open(filename,'rb').read())
encoders.encode_base64(submsg)
submsg.add_header('Content-Disposition', 'attachment', filename=filename)
msg.attach(submsg)
try:
send_smtp = smtplib.SMTP()
send_smtp.connect(mail_host)
send_smtp.login(mail_user, mail_pass)
send_smtp.sendmail(me, to_list, msg.as_string())
send_smtp.close()
return True
except Exception, e:
print str(e)[1]
return False


# 設定伺服器名稱、使用者名稱、密碼以及郵件字尾 
mail_host = "smtp.163.com"
mail_user = "xuesong"
mail_pass = "mailpasswd"
mail_postfix = "163.com"
mailto_list = ["272121935@qq.com","quanzhou722@163.com"]
title = 'check'
filename = 'file_check.html'
if send_mail(mailto_list,title,filename):
print "傳送成功"
else:
print "傳送失敗"


解壓縮


gzip壓縮


import gzip
f_in = open('file.log', 'rb')
f_out = gzip.open('file.log.gz', 'wb')
f_out.writelines(f_in)
f_out.close()
f_in.close()


gzip壓縮1


File = 'xuesong_18.log'
g = gzip.GzipFile(filename="", mode='wb', compresslevel=9, fileobj=open((r'%s.gz' %File),'wb'))
g.write(open(r'%s' %File).read())
g.close()


gzip解壓


g = gzip.GzipFile(mode='rb', fileobj=open((r'xuesong_18.log.gz'),'rb'))
open((r'xuesong_18.log'),'wb').write(g.read())


壓縮tar.gz


import os
import tarfile
tar = tarfile.open("/tmp/tartest.tar.gz","w:gz")   # 建立壓縮包名
for path,dir,files in os.walk("/tmp/tartest"):     # 遞迴檔案目錄
for file in files:
fullpath = os.path.join(path,file)
tar.add(fullpath)                          # 建立壓縮包
tar.close()


解壓tar.gz

import tarfile
tar = tarfile.open("/tmp/tartest.tar.gz")
#tar.extract("/tmp")                           # 全部解壓到指定路徑
names = tar.getnames()                         # 包內檔名
for name in names:
tar.extract(name,path="./")                # 解壓指定檔案
tar.close()


zip壓縮
import zipfile,os
f = zipfile.ZipFile('filename.zip', 'w' ,zipfile.ZIP_DEFLATED)    # ZIP_STORE 為預設表不壓縮. ZIP_DEFLATED 表壓縮
#f.write('file1.txt')                              # 將檔案寫入壓縮包
for path,dir,files in os.walk("tartest"):          # 遞迴壓縮目錄
for file in files:
f.write(os.path.join(path,file))           # 將檔案逐個寫入壓縮包         
f.close()


zip解壓
if zipfile.is_zipfile('filename.zip'):        # 判斷一個檔案是不是zip檔案
f = zipfile.ZipFile('filename.zip')
for file in f.namelist():                 # 返回檔案列表
f.extract(file, r'/tmp/')             # 解壓指定檔案
#f.extractall()                           # 解壓全部
f.close()


時間


import time
time.time()                          # 時間戳[浮點]
time.localtime()[1] - 1              # 上個月
int(time.time())                     # 時間戳[整s]
tomorrow.strftime('%Y%m%d_%H%M')     # 格式化時間
time.strftime('%Y-%m-%d_%X',time.localtime( time.time() ) )              # 時間戳轉日期
time.mktime(time.strptime('2012-03-28 06:53:40', '%Y-%m-%d %H:%M:%S'))   # 日期轉時間戳


判斷輸入時間格式是否正確

#encoding:utf8
import time
while 1:
atime=raw_input('輸入格式如[14.05.13 13:00]:')
try:
btime=time.mktime(time.strptime('%s:00' %atime, '%y.%m.%d %H:%M:%S'))
break
except:
print '時間輸入錯誤,請重新輸入,格式如[14.05.13 13:00]'


上一個月最後一天
import datetime
lastMonth=datetime.date(datetime.date.today().year,datetime.date.today().month,1)-datetime.timedelta(1)
lastMonth.strftime("%Y/%m")


前一天
(datetime.datetime.now() + datetime.timedelta(days=-1) ).strftime('%Y%m%d')


兩日期相差天數


import datetime
d1 = datetime.datetime(2005, 2, 16)
d2 = datetime.datetime(2004, 12, 31)
(d1 - d2).days


向後加10個小時


import datetime
d1 = datetime.datetime.now()
d3 = d1 + datetime.timedelta(hours=10)
d3.ctime()


引數[optparse]
import os, sys
import time
import optparse
# python aaa.py -t file -p /etc/opt -o aaaaa


def do_fiotest( type, path, output,):
print type, path, output,


def main():
parser = optparse.OptionParser()
parser.add_option('-t', '--type', dest = 'type', default = None, help = 'test type[file, device]')
parser.add_option('-p', '--path', dest = 'path', default = None, help = 'test file path or device path')
parser.add_option('-o', '--output', dest = 'output', default = None, help = 'result dir path')


(o, a) = parser.parse_args()


if None == o.type or None == o.path or None == o.output:
print "No device or file or output dir"
return -1


if 'file' != o.type and 'device' != o.type:
print "You need specify test type ['file' or 'device']"
return -1


do_fiotest(o.type, o.path, o.output)
print "Test done!"



if __name__ == '__main__':
main()


hash


import md5
m = md5.new('123456').hexdigest()

import hashlib
m = hashlib.md5()
m.update("Nobody inspects")    # 使用update方法對字串md5加密
m.digest()                     # 加密後二進位制結果
m.hexdigest()                  # 加密後十進位制結果
hashlib.new("md5", "string").hexdigest()               # 對字串加密
hashlib.new("md5", open("file").read()).hexdigest()    # 檢視檔案MD5值


隱藏輸入密碼


import getpass
passwd=getpass.getpass()


string列印a-z
import string
string.lowercase       # a-z小寫
string.uppercase       # A-Z大小


paramiko [ssh客戶端]


安裝
sudo apt-get install python-setuptools 
easy_install
sudo apt-get install python-all-dev
sudo apt-get install build-essential


paramiko例項(賬號密碼登入執行命令)


#!/usr/bin/python
#ssh
import paramiko
import sys,os


host = '10.152.15.200'
user = 'peterli'
password = '123456'


s = paramiko.SSHClient()                                 # 繫結例項
s.load_system_host_keys()                                # 載入本地HOST主機檔案
s.set_missing_host_key_policy(paramiko.AutoAddPolicy())  # 允許連線不在know_hosts檔案中的主機
s.connect(host,22,user,password,timeout=5)               # 連線遠端主機
while True:
cmd=raw_input('cmd:')
stdin,stdout,stderr = s.exec_command(cmd)        # 執行命令
cmd_result = stdout.read(),stderr.read()         # 讀取命令結果
for line in cmd_result:
print line,
s.close()


paramiko例項(傳送檔案)


#!/usr/bin/evn python
import os
import paramiko
host='127.0.0.1'
port=22
username = 'peterli'
password = '123456'
ssh=paramiko.Transport((host,port))
privatekeyfile = os.path.expanduser('~/.ssh/id_rsa') 
mykey = paramiko.RSAKey.from_private_key_file( os.path.expanduser('~/.ssh/id_rsa'))   # 載入key 不使用key可不加
ssh.connect(username=username,password=password)           # 連線遠端主機
# 使用key把 password=password 換成 pkey=mykey
sftp=paramiko.SFTPClient.from_transport(ssh)               # SFTP使用Transport通道
sftp.get('/etc/passwd','pwd1')                             # 下載 兩端都要指定檔名
sftp.put('pwd','/tmp/pwd')                                 # 上傳
sftp.close()
ssh.close()


paramiko例項(金鑰執行命令)


#!/usr/bin/python
#ssh
import paramiko
import sys,os
host = '10.152.15.123'
user = 'peterli'
s = paramiko.SSHClient()
s.load_system_host_keys()
s.set_missing_host_key_policy(paramiko.AutoAddPolicy())
privatekeyfile = os.path.expanduser('~/.ssh/id_rsa')             # 定義key路徑
mykey = paramiko.RSAKey.from_private_key_file(privatekeyfile)
# mykey=paramiko.DSSKey.from_private_key_file(privatekeyfile,password='061128')   # DSSKey方式 password是key的密碼
s.connect(host,22,user,pkey=mykey,timeout=5)
cmd=raw_input('cmd:')
stdin,stdout,stderr = s.exec_command(cmd)
cmd_result = stdout.read(),stderr.read()
for line in cmd_result:
print line,
s.close()


ssh併發(Pool控制最大併發)


#!/usr/bin/env python
#encoding:utf8
#ssh_concurrent.py


import multiprocessing
import sys,os,time
import paramiko


def ssh_cmd(host,port,user,passwd,cmd):
msg = "-----------Result:%s----------" % host


s = paramiko.SSHClient()
s.load_system_host_keys()
s.set_missing_host_key_policy(paramiko.AutoAddPolicy())
try:
s.connect(host,22,user,passwd,timeout=5) 
stdin,stdout,stderr = s.exec_command(cmd)


cmd_result = stdout.read(),stderr.read()
print msg
for line in cmd_result:
print line,


s.close()
except paramiko.AuthenticationException:
print msg
print 'AuthenticationException Failed'
except paramiko.BadHostKeyException:
print msg
print "Bad host key"


result = []
p = multiprocessing.Pool(processes=20)
cmd=raw_input('CMD:')
f=open('serverlist.conf')
list = f.readlines()
f.close()
for IP in list:
print IP
host=IP.split()[0]
port=int(IP.split()[1])
user=IP.split()[2]
passwd=IP.split()[3]
result.append(p.apply_async(ssh_cmd,(host,port,user,passwd,cmd)))


p.close()


for res in result:
res.get(timeout=35)


ssh併發(取檔案狀態併傳送郵件)


#!/usr/bin/python
#encoding:utf8
#config file: ip.list


import paramiko
import multiprocessing
import smtplib
import sys,os,time,datetime,socket,re
from email.mime.text import MIMEText


# 配置檔案(IP列表)
Conf = 'ip.list'
user_name = 'peterli'
user_pwd = 'passwd'
port = 22
PATH = '/home/peterli/'


# 設定伺服器名稱、使用者名稱、密碼以及郵件字尾 
mail_host = "smtp.163.com"
mail_user = "xuesong"
mail_pass = "mailpasswd"
mail_postfix = "163.com"
mailto_list = ["272121935@qq.com","quanzhou722@163.com"]
title = 'file check'


DATE1=(datetime.datetime.now() + datetime.timedelta(days=-1) ).strftime('%Y%m%d')
file_path = '%s%s' %(PATH,DATE1)


def Ssh_Cmd(file_path,host_ip,user_name,user_pwd,port=22):


s = paramiko.SSHClient()
s.load_system_host_keys()
s.set_missing_host_key_policy(paramiko.AutoAddPolicy())

try:
s.connect(hostname=host_ip,port=port,username=user_name,password=user_pwd)
stdin,stdout,stderr = s.exec_command('stat %s' %file_path)
stat_result = '%s%s' %(stdout.read(),stderr.read())
if stat_result.find('No such file or directory') == -1:
file_status = 'OK\t'
stdin,stdout,stderr = s.exec_command('du -sh %s' %file_path)
cmd1_result = '%s_%s' %(stat_result.split()[32],stat_result.split()[33].split('.')[0])
cmd2_result = ('%s%s' %(stdout.read(),stderr.read())).split()[0] 
else:
file_status = '未生成\t'
cmd1_result = 'null'
cmd2_result = 'null'
q.put(['Login successful'])
s.close()
except socket.error:
file_status = '主機或埠錯誤'
cmd1_result = '-'
cmd2_result = '-'
except paramiko.AuthenticationException:
file_status = '使用者或密碼錯誤'
cmd1_result = '-'
cmd2_result = '-'
except paramiko.BadHostKeyException:
file_status = 'Bad host key'
cmd1_result = '-'
cmd2_result = '-'
except:
file_status = 'ssh異常'
cmd1_result = '-'
cmd2_result = '-'
r.put('%s\t-\t%s\t%s\t%s\t%s\n' %(time.strftime('%Y-%m-%d_%H:%M'),host_ip,file_status,cmd2_result,cmd1_result))


def Concurrent(Conf,file_path,user_name,user_pwd,port):
# 執行總計
total = 0
# 讀取配置檔案
f=open(Conf)
list = f.readlines()
f.close()
# 併發執行
process_list = []
log_file = file('file_check.log', 'w')
log_file.write('檢查時間\t\t業務\tIP\t\t檔案狀態\t大小\t生成時間\n') 
for host_info in list:
# 判斷配置檔案中註釋行跳過
if host_info.startswith('#'):
continue
# 取變數,其中任意變數未取到就跳過執行
try:
host_ip=host_info.split()[0].strip()
#user_name=host_info.split()[1]
#user_pwd=host_info.split()[2]
except:
log_file.write('Profile error: %s\n' %(host_info))
continue
#try:
# port=int(host_info.split()[3])
#except:
# port=22
total +=1
p = multiprocessing.Process(target=Ssh_Cmd,args=(file_path,host_ip,user_name,user_pwd,port))
p.start()
process_list.append(p)
for j in process_list:
j.join()
for j in process_list:
log_file.write(r.get())


successful = q.qsize()
log_file.write('執行完畢。 總執行:%s 登入成功:%s 登入失敗:%s\n' %(total,successful,total - successful))
log_file.flush()
log_file.close()


def send_mail(to_list, sub):
me = mail_user + "<"+mail_user+"@"+mail_postfix+">"
fp = open('file_check.log')
msg = MIMEText(fp.read(),_charset="utf-8")
fp.close()
msg['Subject'] = sub
msg['From'] = me
msg['To'] = ";".join(to_list)
try:
send_smtp = smtplib.SMTP()
send_smtp.connect(mail_host)
send_smtp.login(mail_user, mail_pass)
send_smtp.sendmail(me, to_list, msg.as_string())
send_smtp.close()
return True
except Exception, e:
print str(e)[1]
return False


if __name__ == '__main__':
q = multiprocessing.Queue()
r = multiprocessing.Queue()
Concurrent(Conf,file_path,user_name,user_pwd,port)
if send_mail(mailto_list,title):
print "傳送成功"
else:
print "傳送失敗"


LazyManage併發批量操作(判斷非root互動到root操作)


#!/usr/bin/python
#encoding:utf8
# LzayManage.py
# config file: serverlist.conf


import paramiko
import multiprocessing
import sys,os,time,socket,re


def Ssh_Cmd(host_ip,Cmd,user_name,user_pwd,port=22):
s = paramiko.SSHClient()
s.load_system_host_keys()
s.set_missing_host_key_policy(paramiko.AutoAddPolicy())
s.connect(hostname=host_ip,port=port,username=user_name,password=user_pwd)
stdin,stdout,stderr = s.exec_command(Cmd)
Result = '%s%s' %(stdout.read(),stderr.read())
q.put('successful')
s.close()
return Result.strip()


def Ssh_Su_Cmd(host_ip,Cmd,user_name,user_pwd,root_name,root_pwd,port=22):
s = paramiko.SSHClient()
s.load_system_host_keys()
s.set_missing_host_key_policy(paramiko.AutoAddPolicy())
s.connect(hostname=host_ip,port=port,username=user_name,password=user_pwd)
ssh = s.invoke_shell()
time.sleep(0.1)
ssh.send('su - %s\n' %(root_name))
buff = ''
while not buff.endswith('Password: '):
resp = ssh.recv(9999)
buff +=resp
ssh.send('%s\n' %(root_pwd))
buff = ''
while True:
resp = ssh.recv(9999)
buff +=resp
if ': incorrect password' in buff:
su_correct='passwd_error'
break
elif buff.endswith('# '):
su_correct='passwd_correct'
break
if su_correct == 'passwd_correct':
ssh.send('%s\n' %(Cmd))
buff = ''
while True:
resp = ssh.recv(9999)
if resp.endswith('# '):
buff +=re.sub('\[.*@.*\]# $','',resp)
break
buff +=resp
Result = buff.lstrip('%s' %(Cmd))
q.put('successful')
elif su_correct == 'passwd_error':
Result = "\033[31mroot密碼錯誤\033[m"
s.close()
return Result.strip()


def Send_File(host_ip,PathList,user_name,user_pwd,Remote='/tmp',port=22):
s=paramiko.Transport((host_ip,port))
s.connect(username=user_name,password=user_pwd)
sftp=paramiko.SFTPClient.from_transport(s) 
for InputPath in PathList:
LocalPath = re.sub('^\./','',InputPath.rstrip('/'))
RemotePath = '%s/%s' %( Remote , os.path.basename( LocalPath ))
try:
sftp.rmdir(RemotePath)
except:
pass
try:
sftp.remove(RemotePath)
except:
pass
if os.path.isdir(LocalPath):
sftp.mkdir(RemotePath)
for path,dirs,files in os.walk(LocalPath):
for dir in dirs:
dir_path = os.path.join(path,dir)
sftp.mkdir('%s/%s' %(RemotePath,re.sub('^%s/' %LocalPath,'',dir_path)))
for file in files:
file_path = os.path.join(path,file)
sftp.put( file_path,'%s/%s' %(RemotePath,re.sub('^%s/' %LocalPath,'',file_path)))
else:
sftp.put(LocalPath,RemotePath)
q.put('successful')
sftp.close()
s.close()
Result = '%s  \033[32m傳送完成\033[m' % PathList
return Result


def Ssh(host_ip,Operation,user_name,user_pwd,root_name,root_pwd,Cmd=None,PathList=None,port=22):
msg = "\033[32m-----------Result:%s----------\033[m" % host_ip
try:
if Operation == 'Ssh_Cmd':
Result = Ssh_Cmd(host_ip=host_ip,Cmd=Cmd,user_name=user_name,user_pwd=user_pwd,port=port)
elif Operation == 'Ssh_Su_Cmd':
Result = Ssh_Su_Cmd(host_ip=host_ip,Cmd=Cmd,user_name=user_name,user_pwd=user_pwd,root_name=root_name,root_pwd=root_pwd,port=port)
elif Operation == 'Ssh_Script':
Send_File(host_ip=host_ip,PathList=PathList,user_name=user_name,user_pwd=user_pwd,port=port)
Script_Head = open(PathList[0]).readline().strip()
LocalPath = re.sub('^\./','',PathList[0].rstrip('/'))
Cmd = '%s /tmp/%s' %( re.sub('^#!','',Script_Head), os.path.basename( LocalPath ))
Result = Ssh_Cmd(host_ip=host_ip,Cmd=Cmd,user_name=user_name,user_pwd=user_pwd,port=port)
elif Operation == 'Ssh_Su_Script':
Send_File(host_ip=host_ip,PathList=PathList,user_name=user_name,user_pwd=user_pwd,port=port)
Script_Head = open(PathList[0]).readline().strip()
LocalPath = re.sub('^\./','',PathList[0].rstrip('/'))
Cmd = '%s /tmp/%s' %( re.sub('^#!','',Script_Head), os.path.basename( LocalPath ))
Result = Ssh_Su_Cmd(host_ip=host_ip,Cmd=Cmd,user_name=user_name,user_pwd=user_pwd,root_name=root_name,root_pwd=root_pwd,port=port)
elif Operation == 'Send_File':
Result = Send_File(host_ip=host_ip,PathList=PathList,user_name=user_name,user_pwd=user_pwd,port=port)
else:
Result = '操作不存在'

except socket.error:
Result = '\033[31m主機或埠錯誤\033[m'
except paramiko.AuthenticationException:
Result = '\033[31m使用者名稱或密碼錯誤\033[m'
except paramiko.BadHostKeyException:
Result = '\033[31mBad host key\033[m['
except IOError:
Result = '\033[31m遠端主機已存在非空目錄或沒有寫許可權\033[m'
except:
Result = '\033[31m未知錯誤\033[m'
r.put('%s\n%s\n' %(msg,Result))


def Concurrent(Conf,Operation,user_name,user_pwd,root_name,root_pwd,Cmd=None,PathList=None,port=22):
# 讀取配置檔案
f=open(Conf)
list = f.readlines()
f.close()
# 執行總計
total = 0
# 併發執行
for host_info in list:
# 判斷配置檔案中註釋行跳過
if host_info.startswith('#'):
continue
# 取變數,其中任意變數未取到就跳過執行
try:
host_ip=host_info.split()[0]
#user_name=host_info.split()[1]
#user_pwd=host_info.split()[2]
except:
print('Profile error: %s' %(host_info) )
continue
try:
port=int(host_info.split()[3])
except:
port=22
total +=1
p = multiprocessing.Process(target=Ssh,args=(host_ip,Operation,user_name,user_pwd,root_name,root_pwd,Cmd,PathList,port))
p.start()
# 列印執行結果
for j in range(total):
print(r.get() )
if Operation == 'Ssh_Script' or Operation == 'Ssh_Su_Script':
successful = q.qsize() / 2
else:
successful = q.qsize()
print('\033[32m執行完畢[總執行:%s 成功:%s 失敗:%s]\033[m' %(total,successful,total - successful) )
q.close()
r.close()


def Help():
print(''' 1.執行命令
2.執行指令碼      \033[32m[位置1指令碼(必須帶指令碼頭),後可帶執行指令碼所需要的包\檔案\資料夾路徑,空格分隔]\033[m
3.傳送檔案      \033[32m[傳送的包\檔案\資料夾路徑,空格分隔]\033[m
退出: 0\exit\quit
幫助: help\h\?
注意: 傳送檔案預設為/tmp下,如已存在同名檔案會被強制覆蓋,非空目錄則中斷操作.執行指令碼先將本地指令碼及包傳送遠端主機上,傳送規則同傳送檔案
''')


if __name__=='__main__':
# 定義root賬號資訊
root_name = 'root'
root_pwd = 'peterli'
user_name='peterli'
user_pwd='<++(3Ie'
# 配置檔案
Conf='serverlist.conf'
if not os.path.isfile(Conf):
print('\033[33m配置檔案 %s 不存在\033[m' %(Conf) )
sys.exit()
Help()
while True:
i = raw_input("\033[35m[請選擇操作]: \033[m").strip()
q = multiprocessing.Queue()
r = multiprocessing.Queue()
if i == '1':
if user_name == root_name:
Operation = 'Ssh_Cmd'
else:
Operation = 'Ssh_Su_Cmd'
Cmd = raw_input('CMD: ').strip()
if len(Cmd) == 0:
print('\033[33m命令為空\033[m')
continue
Concurrent(Conf=Conf,Operation=Operation,user_name=user_name,user_pwd=user_pwd,root_name=root_name,root_pwd=root_pwd,Cmd=Cmd)
elif i == '2':
if user_name == root_name:
Operation = 'Ssh_Script'
else:
Operation = 'Ssh_Su_Script'
PathList = raw_input('\033[36m本地指令碼路徑: \033[m').strip().split()
if len(PathList) == 0:
print('\033[33m路徑為空\033[m')
continue
if not os.path.isfile(PathList[0]):
print('\033[33m本地路徑 %s 不存在或不是檔案\033[m' %(PathList[0]) )
continue
for LocalPath in PathList[1:]:
if not os.path.exists(LocalPath):
print('\033[33m本地路徑 %s 不存在\033[m' %(LocalPath) )
break
else:
Concurrent(Conf=Conf,Operation=Operation,user_name=user_name,user_pwd=user_pwd,root_name=root_name,root_pwd=root_pwd,PathList=PathList)
elif i == '3':
Operation = 'Send_File'
PathList = raw_input('\033[36m本地路徑: \033[m').strip().split()
if len(PathList) == 0:
print('\033[33m路徑為空\033[m')
continue
for LocalPath in PathList:
if not os.path.exists(LocalPath):
print('\033[33m本地路徑 %s 不存在\033[m' %(LocalPath) )
break
else:
Concurrent(Conf=Conf,Operation=Operation,user_name=user_name,user_pwd=user_pwd,root_name=root_name,root_pwd=root_pwd,PathList=PathList)
elif i == '0' or i == 'exit' or i == 'quit':
print("\033[34m退出LazyManage指令碼\033[m")
sys.exit()
elif i == 'help' or i == 'h' or i == '?':
Help()


pysnmp

#!/usr/bin/python
from pysnmp.entity.rfc3413.oneliner import cmdgen


cg = cmdgen.CommandGenerator()


# 注意IP 埠 組預設public  oid值
varBinds = cg.getCmd( cmdgen.CommunityData('any-agent', 'public',0 ), cmdgen.UdpTransportTarget(('10.10.76.42', 161)),    (1,3,6,1,4,1,2021,10,1,3,1), )


print varBinds[3][0][1]


3 socket


socket.gethostname()     # 獲取主機名
from socket import *     # 避免 socket.socket()
s=socket()
s.bind()         # 繫結地址到套接字
s.listen()       # 開始TCP監聽
s.accept()       # 被動接受TCP客戶端連線,等待連線的到來
s.connect()      # 主動初始化TCP伺服器連線
s.connect_ex()   # connect()函式的擴充套件版本,出錯時返回出錯碼,而不是跑出異常
s.recv()         # 接收TCP資料
s.send()         # 傳送TCP資料
s.sendall()      # 完整傳送TCP資料
s.recvfrom()     # 接收UDP資料
s.sendto()       # 傳送UDP資料
s.getpeername()  # 連線到當前套接字的遠端的地址(TCP連線)
s.getsockname()  # 當前套接字的地址
s.getsockopt()   # 返回指定套接字的引數
s.setsockopt()   # 設定指定套接字的引數
s.close()        # 關閉套接字
s.setblocking()  # 設定套接字的阻塞與非阻塞模式
s.settimeout()   # 設定阻塞套接字操作的超時時間
s.gettimeout()   # 得到阻塞套接字操作的超時時間
s.filen0()       # 套接字的檔案描述符
s.makefile()     # 建立一個與該套接字關聯的檔案物件


socket.AF_UNIX # 只能夠用於單一的Unix系統程式間通訊
socket.AF_INET # 伺服器之間網路通訊
socket.AF_INET6 # IPv6


socket.SOCK_STREAM  # 流式socket , for TCP
socket.SOCK_DGRAM  # 資料包式socket , for UDP
socket.SOCK_RAW      # 原始套接字,普通的套接字無法處理ICMP、IGMP等網路報文,而SOCK_RAW可以;其次,SOCK_RAW也可以處理特殊的IPv4報文;此外,利用原始套接字,可以通過IP_HDRINCL套接字選項由使用者構造IP頭。


socket.SOCK_RDM  # 是一種可靠的UDP形式,即保證交付資料包但不保證順序。SOCK_RAM用來提供對原始協議的低階訪問,在需要執行某些特殊操作時使用,如傳送ICMP報文。SOCK_RAM通常僅限於高階使用者或管理員執行的程式使用。


socket.SOCK_SEQPACKET # 可靠的連續資料包服務


SocketServer

#!/usr/bin/python
#server.py
import SocketServer
import os
class MyTCP(SocketServer.BaseRequestHandler):
def handle(self):
while True:
self.data=self.request.recv(1024).strip()
if self.data == 'quit' or not self.data:break

cmd=os.popen(self.data).read()
if cmd == '':cmd= self.data + ': Command not found'
self.request.sendall(cmd)
if __name__ == '__main__':
HOST,PORT = '10.0.0.119',50007
server = SocketServer.ThreadingTCPServer((HOST,PORT),MyTCP)
server.serve_forever()


SocketClient


#!/usr/bin/python
#client.py
import socket


HOST='10.0.0.119'
PORT=50007
s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.connect((HOST,PORT))


while True:
while True:
cmd=raw_input('CMD:').strip()
if cmd != '':break
s.sendall(cmd)      
data=s.recv(1024).split('\n')
print 'cmd:'
for line in data:print line
s.close()


ftp


ftpserver


#!/usr/bin/python
#ftpserver.py


import SocketServer
import os
import cPickle
import md5
from time import sleep


def filer(file1):
try:
f = file(file1,'rb')
return cPickle.load(f)
except IOError:
return {}
except EOFError:
return {}
f.close()


def filew(file1,content):
f = file(file1,'wb')
cPickle.dump(content,f)
f.close()


class MyTCP(SocketServer.BaseRequestHandler):
def handle(self):
i = 0
while i<3:
user=self.request.recv(1024).strip()
userinfo=filer('user.pkl')
if userinfo.has_key(user.split()[0]):
if md5.new(user.split()[1]).hexdigest() == userinfo[user.split()[0]]:
results='login successful'
self.request.sendall(results)
login='successful'
break
else:
i = i + 1
results='Error:password not correct'
self.request.sendall(results)
continue
else:
i = i + 1
results='Error:password not correct'
self.request.sendall(results)
continue
break
else:
results = 'Error:Wrong password too many times'
self.request.sendall(results)
login='failure'
home_path = os.popen('pwd').read().strip() + '/' + user.split()[0]
current_path = '/'
print home_path
while True:
if login == 'failure':
break
print 'home_path:%s=current_path:%s' %(home_path,current_path)
cmd=self.request.recv(1024).strip()
print cmd
if cmd == 'quit':
break
elif cmd == 'dir':
list=os.listdir('%s%s' %(home_path,current_path))
if list:
dirlist,filelist = '',''
for i in list:
if os.path.isdir('%s%s%s' %(home_path,current_path,i)):
dirlist = dirlist + '\033[32m' + i + '\033[m\t'
else:
filelist = filelist + i + '\t'
results = dirlist + filelist
else:
results = '\033[31mnot find\033[m'
self.request.sendall(results)
elif cmd == 'pdir':
self.request.sendall(current_path)
elif cmd.split()[0] == 'mdir':
if cmd.split()[1].isalnum():
tmppath='%s%s%s' %(home_path,current_path,cmd.split()[1])
os.makedirs(tmppath)
self.request.sendall('\033[32mcreating successful\033[m')
else:
self.request.sendall('\033[31mcreate failure\033[m')
elif cmd.split()[0] == 'cdir':
if cmd.split()[1] == '/':
tmppath='%s%s' %(home_path,cmd.split()[1])
if os.path.isdir(tmppath):
current_path = cmd.split()[1]
self.request.sendall(current_path)
else:
self.request.sendall('\033[31mnot_directory\033[m')
elif cmd.split()[1].startswith('/'):
tmppath='%s%s' %(home_path,cmd.split()[1])
if os.path.isdir(tmppath):
current_path = cmd.split()[1] + '/'
self.request.sendall(current_path)
else:
self.request.sendall('\033[31mnot_directory\033[m')
else:
tmppath='%s%s%s' %(home_path,current_path,cmd.split()[1])
if os.path.isdir(tmppath):
current_path = current_path + cmd.split()[1] + '/'
self.request.sendall(current_path)
else:
self.request.sendall('\033[31mnot_directory\033[m')
elif cmd.split()[0] == 'get':
if os.path.isfile('%s%s%s' %(home_path,current_path,cmd.split()[1])):
f = file('%s%s%s' %(home_path,current_path,cmd.split()[1]),'rb')
self.request.sendall('ready_file')
sleep(0.5)
self.request.send(f.read())
f.close()
sleep(0.5)
elif os.path.isdir('%s%s%s' %(home_path,current_path,cmd.split()[1])):
self.request.sendall('ready_dir')
sleep(0.5)
for dirpath in os.walk('%s%s%s' %(home_path,current_path,cmd.split()[1])):
dir=dirpath[0].replace('%s%s' %(home_path,current_path),'',1)
self.request.sendall(dir)
sleep(0.5)
for filename in dirpath[2]:
self.request.sendall(filename)
sleep(0.5)
f = file('%s/%s' %(dirpath[0],filename),'rb')
self.request.send(f.read())
f.close()
sleep(0.5)
self.request.sendall('file_get_done')
sleep(0.5)
else:
self.request.sendall('dir_get_done')
sleep(0.5)
else:
self.request.sendall('get_failure')
continue
self.request.sendall('get_done')

elif cmd.split()[0] == 'send':
if os.path.exists('%s%s%s' %(home_path,current_path,cmd.split()[1])):
self.request.sendall('existing')
action=self.request.recv(1024)
if action == 'cancel':
continue
self.request.sendall('ready')
msg=self.request.recv(1024)
if msg == 'ready_file':
f = file('%s%s%s' %(home_path,current_path,cmd.split()[1]),'wb')
while True:
data=self.request.recv(1024)
if data == 'file_send_done':break
f.write(data)
f.close()


elif msg == 'ready_dir':
os.system('mkdir -p %s%s%s' %(home_path,current_path,cmd.split()[1]))
while True:
dir=self.request.recv(1024)
if dir == 'get_done':break
os.system('mkdir -p %s%s%s' %(home_path,current_path,dir))
while True:
filename=self.request.recv(1024)
if filename == 'dir_send_done':break
f = file('%s%s%s/%s' %(home_path,current_path,dir,filename),'wb')
while True:
data=self.request.recv(1024)
if data == 'file_send_done':break 
f.write(data)
f.close()
self.request.sendall('%s/%s\t\033[32mfile_done\033[m' %(dir,filename))
self.request.sendall('%s\t\033[32mdir_done\033[m' %(dir))
elif msg == 'unknown_file':
continue

else:
results = cmd.split()[0] + ': Command not found'
self.request.sendall(results)


if __name__ == '__main__':
HOST,PORT = '10.152.14.85',50007
server = SocketServer.ThreadingTCPServer((HOST,PORT),MyTCP)
server.serve_forever()


ftpmanage


#!/usr/bin/python
#manage_ftp.py
import cPickle
import sys
import md5
import os
import getpass


def filer(file1):
try:
f = file(file1,'rb')
return cPickle.load(f)
except IOError:
return {}
except EOFError:
return {}
f.close()


def filew(file1,content):
f = file(file1,'wb')
cPickle.dump(content,f)
f.close()


while True:
print '''
1.add user
2.del user
3.change password
4.query user
0.exit
'''
i = raw_input(':').strip()
userinfo=filer('user.pkl')
if i == '':
continue
elif i == '1':
while True:
user=raw_input('user name:').strip()
if user.isalnum():
i = 0
while i<3:
passwd=getpass.getpass('passwd:').strip()
if passwd == '':
continue
else:
passwd1=getpass.getpass('Confirm password:').strip()
if passwd == passwd1:
mpasswd = md5.new(passwd).hexdigest()
userinfo[user] = mpasswd
os.system('mkdir -p %s' %user)
print '%s creating successful ' %user
break
else:
print "Passwords don't match "
i = i + 1
continue
else:
print 'Too many wrong'
continue
break
else:
print 'user not legal'
continue
elif i == '2':
user=raw_input('user name:').strip()
if userinfo.has_key(user):
del userinfo[user]
print 'Delete users successfully'
else:
print 'user not exist'
continue
elif i == '3':
user=raw_input('user name:').strip()
if userinfo.has_key(user):
i = 0
while i<3:
passwd=getpass.getpass('passwd:').strip()
if passwd == '':
continue
else:
passwd1=getpass.getpass('Confirm password:').strip()
if passwd == passwd1:
mpasswd = md5.new(passwd).hexdigest()
userinfo[user] = mpasswd
print '%s password is changed' %user
break
else:
print "Passwords don't match "
i = i + 1
continue
else:
print 'Too many wrong'
continue
else:
print 'user not exist'
continue
elif i == '4':
print userinfo.keys()
elif i == '0':
sys.exit()
else:
print 'select error'
continue
filew('user.pkl',content=userinfo)

ftpclient


#!/usr/bin/python
#ftpclient.py


import socket
import os
import getpass
from time import sleep


HOST='10.152.14.85'
PORT=50007
s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.connect((HOST,PORT))

while True:
user = raw_input('user:').strip()
if user.isalnum():
while True:
passwd = getpass.getpass('passwd:').strip()
s.sendall(user + ' ' + passwd)
servercmd=s.recv(1024)
if servercmd == 'login successful':
print '\033[32m%s\033[m' %servercmd
break
else:
print servercmd


while True:
cmd=raw_input('FTP>').strip()
if cmd == '':
continue
if cmd.split()[0] == 'get':
if cmd == 'get':continue
for i in cmd.split()[1:]:
if os.path.exists(i):
confirm = raw_input("\033[31mPlease confirm whether the cover %s(Y/N):\033[m" %(i)).upper().startswith('Y')
if not confirm:
print '%s cancel' %i
continue
s.sendall('get ' + i)
servercmd=s.recv(1024)
if servercmd == 'inexistence':
print '%s \t\033[32minexistence\033[m' %i
continue
elif servercmd == 'ready_file':
f = file(i,'wb')
while True:
data=s.recv(1024)
if data == 'get_done':break 
f.write(data)
f.close()
print '%s \t\033[32mfile_done\033[m' %(i)
elif servercmd == 'ready_dir':
try:
os.makedirs(i)
except:
pass
while True:
serverdir=s.recv(1024)
if serverdir == 'get_done':break 
os.system('mkdir -p %s' %serverdir)
print '%s \t\033[32mdir_done\033[m' %(serverdir)
while True:
serverfile=s.recv(1024)
if serverfile == 'dir_get_done':break 
f = file('%s/%s' %(serverdir,serverfile),'wb')
while True:
data=s.recv(1024)
if data == 'file_get_done':break 
f.write(data)
f.close()
print '%s/%s \t\033[32mfile_done\033[m' %(serverdir,serverfile)


elif cmd.split()[0] == 'send':

if cmd == 'send':continue
for i in cmd.split()[1:]:
if not os.path.exists(i):
print '%s\t\033[31minexistence\033[m' %i
continue

s.sendall('send ' + i)
servercmd=s.recv(1024)
if servercmd == 'existing':
confirm = raw_input("\033[31mPlease confirm whether the cover %s(Y/N):\033[m" %(i)).upper().startswith('Y')
if confirm:
s.sendall('cover')
servercmd=s.recv(1024)
else:
s.sendall('cancel')
print '%s\tcancel' %i
continue

if os.path.isfile(i):
s.sendall('ready_file')
sleep(0.5)
f = file(i,'rb')
s.send(f.read())
sleep(0.5)
s.sendall('file_send_done')
print '%s\t\033[32mfile done\033[m' %(cmd.split()[1])
f.close()
elif os.path.isdir(i):
s.sendall('ready_dir')
sleep(0.5)
for dirpath in os.walk(i):
dir=dirpath[0].replace('%s/' %os.popen('pwd').read().strip(),'',1)
s.sendall(dir)
sleep(0.5)
for filename in dirpath[2]:
s.sendall(filename)
sleep(0.5)
f = file('%s/%s' %(dirpath[0],filename),'rb')
s.send(f.read())
f.close()
sleep(0.5)
s.sendall('file_send_done')
msg=s.recv(1024)
print msg


else:
s.sendall('dir_send_done')
msg=s.recv(1024)
print msg

else:
s.sendall('unknown_file')
print '%s\t\033[31munknown type\033[m' %i
continue
sleep(0.5)
s.sendall('get_done')

elif cmd.split()[0] == 'cdir':
if cmd == 'cdir':continue
s.sendall(cmd)
data=s.recv(1024)
print data
continue
elif cmd == 'ls':
list=os.popen(cmd).read().strip().split('\n')
if list:
dirlist,filelist = '',''
for i in list:
if os.path.isdir(i):
dirlist = dirlist + '\033[32m' + i + '\033[m\t'
else:
filelist = filelist + i + '\t'
results = dirlist + filelist
else:
results = '\033[31mnot find\033[m'
print results
continue
elif cmd == 'pwd':
os.system(cmd)
elif cmd.split()[0] == 'cd':
try:
os.chdir(cmd.split()[1])
except:
print '\033[31mcd failure\033[m'
elif cmd == 'dir':
s.sendall(cmd)
data=s.recv(1024)
print data
continue
elif cmd == 'pdir':
s.sendall(cmd)
data=s.recv(1024)
print data
continue
elif cmd.split()[0] == 'mdir':
if cmd == 'mdir':continue
s.sendall(cmd)
data=s.recv(1024)
print data
continue
elif cmd.split()[0] == 'help':
print '''
get [file] [dir]
send [file] [dir]


dir
mdir
cdir
pdir

pwd
md
cd
ls

help
quit
'''
continue
elif cmd == 'quit':
break
else:
print '\033[31m%s: Command not found,Please see the "help"\033[m' %cmd
else:
continue
break
s.close()


掃描主機開放埠
#!/usr/bin/env python


import socket


def check_server(address,port):
s=socket.socket()
try:
s.connect((address,port))
return True
except socket.error,e:
return False


if __name__=='__main__':
from optparse import OptionParser
parser=OptionParser()
parser.add_option("-a","--address",dest="address",default='localhost',help="Address for server",metavar="ADDRESS")
parser.add_option("-s","--start",dest="start_port",type="int",default=1,help="start port",metavar="SPORT")
parser.add_option("-e","--end",dest="end_port",type="int",default=1,help="end port",metavar="EPORT")
(options,args)=parser.parse_args()
print 'options: %s, args: %s' % (options, args)
port=options.start_port
while(port<=options.end_port):
check = check_server(options.address, port)
if (check):
print 'Port  %s is on' % port
port=port+1


4 mysql

#apt-get install mysql-server
#apt-get install python-MySQLdb
help(MySQLdb.connections.Connection)      # 檢視連結引數


conn=MySQLdb.connect(host='localhost',user='root',passwd='123456',db='fortress',port=3306)    # 定義連線
#conn=MySQLdb.connect(unix_socket='/var/run/mysqld/mysqld.sock',user='root',passwd='123456')   # 使用socket檔案連結
cur=conn.cursor()                                            # 定義遊標
conn.select_db('fortress')                                   # 選擇資料庫
sqlcmd = 'insert into user(name,age) value(%s,%s)'           # 定義sql命令
cur.executemany(sqlcmd,[('aa',1),('bb',2),('cc',3)])         # 插入多條值
cur.execute('delete from user where id=20')                  # 刪除一條記錄
cur.execute("update user set name='a' where id=20")          # 更細資料
sqlresult = cur.fetchall()                                   # 接收全部返回結果
conn.commit()                                                # 提交
cur.close()                                                  # 關閉遊標
conn.close()                                                 # 關閉連線

import MySQLdb
def mydb(dbcmdlist):
try:
conn=MySQLdb.connect(host='localhost',user='root',passwd='123456',db='fortress',port=3306)
cur=conn.cursor()

cur.execute('create database if not exists fortress;')  # 建立資料庫
conn.select_db('fortress')                              # 選擇資料庫
cur.execute('drop table if exists log;')                # 刪除表
cur.execute('CREATE TABLE log ( id BIGINT(20) NOT NULL AUTO_INCREMENT, loginuser VARCHAR(50) DEFAULT NULL, remoteip VARCHAR(50) DEFAULT NULL, PRIMARY KEY (id) );')  # 建立表

result=[]
for dbcmd in dbcmdlist:
cur.execute(dbcmd)           # 執行sql
sqlresult = cur.fetchall()   # 接收全部返回結果
result.append(sqlresult)
conn.commit()                    # 提交
cur.close()
conn.close()
return result
except MySQLdb.Error,e:
print 'mysql error msg: ',e
sqlcmd=[]
sqlcmd.append("insert into log (loginuser,remoteip)values('%s','%s');" %(loginuser,remoteip))
mydb(sqlcmd)


sqlcmd=[]
sqlcmd.append("select * from log;")
result = mydb(sqlcmd)
for i in result[0]:
print i


5 處理訊號


訊號的概念


訊號(signal): 程式之間通訊的方式,是一種軟體中斷。一個程式一旦接收到訊號就會打斷原來的程式執行流程來處理訊號。
傳送訊號一般有兩種原因:
1(被動式)  核心檢測到一個系統事件.例如子程式退出會像父程式傳送SIGCHLD訊號.鍵盤按下control+c會傳送SIGINT訊號
2(主動式)  通過系統呼叫kill來向指定程式傳送訊號
作業系統規定了程式收到訊號以後的預設行為,可以通過繫結訊號處理函式來修改程式收到訊號以後的行為,有兩個訊號是不可更改的 SIGTOP 和 SIGKILL
如果一個程式收到一個SIGUSR1訊號,然後執行訊號繫結函式,第二個SIGUSR2訊號又來了,第一個訊號沒有被處理完畢的話,第二個訊號就會丟棄。
程式結束訊號 SIGTERM 和 SIGKILL 的區別:  SIGTERM 比較友好,程式能捕捉這個訊號,根據您的需要來關閉程式。在關閉程式之前,您可以結束開啟的記錄檔案和完成正在做的任務。在某些情況下,假如程式正在進行作業而且不能中斷,那麼程式可以忽略這個SIGTERM訊號。


常見訊號
kill -l      # 檢視linux提供的訊號


SIGHUP  1          A     # 終端掛起或者控制程式終止
SIGINT  2          A     # 鍵盤終端程式(如control+c)
SIGQUIT 3          C     # 鍵盤的退出鍵被按下
SIGILL  4          C     # 非法指令
SIGABRT 6          C     # 由abort(3)發出的退出指令
SIGFPE  8          C     # 浮點異常
SIGKILL 9          AEF   # Kill訊號  立刻停止
SIGSEGV 11         C     # 無效的記憶體引用
SIGPIPE 13         A     # 管道破裂: 寫一個沒有讀埠的管道
SIGALRM 14         A     # 鬧鐘訊號 由alarm(2)發出的訊號 
SIGTERM 15         A     # 終止訊號,可讓程式安全退出 kill -15
SIGUSR1 30,10,16   A     # 使用者自定義訊號1
SIGUSR2 31,12,17   A     # 使用者自定義訊號2
SIGCHLD 20,17,18   B     # 子程式結束自動向父程式傳送SIGCHLD訊號
SIGCONT 19,18,25         # 程式繼續(曾被停止的程式)
SIGSTOP 17,19,23   DEF   # 終止程式
SIGTSTP 18,20,24   D     # 控制終端(tty)上按下停止鍵
SIGTTIN 21,21,26   D     # 後臺程式企圖從控制終端讀
SIGTTOU 22,22,27   D     # 後臺程式企圖從控制終端寫

預設處理動作一項中的字母含義如下:
A  預設的動作是終止程式
B  預設的動作是忽略此訊號,將該訊號丟棄,不做處理
C  預設的動作是終止程式並進行核心映像轉儲(dump core),核心映像轉儲是指將程式資料在記憶體的映像和程式在核心結構中的部分內容以一定格式轉儲到檔案系統,並且程式退出執行,這樣做的好處是為程式設計師提供了方便,使得他們可以得到程式當時執行時的資料值,允許他們確定轉儲的原因,並且可以除錯他們的程式。
D  預設的動作是停止程式,進入停止狀況以後還能重新進行下去,一般是在除錯的過程中(例如ptrace系統呼叫)
E  訊號不能被捕獲
F  訊號不能被忽略


Python提供的訊號
import signal
dir(signal)
['NSIG', 'SIGABRT', 'SIGALRM', 'SIGBUS', 'SIGCHLD', 'SIGCLD', 'SIGCONT', 'SIGFPE', 'SIGHUP', 'SIGILL', 'SIGINT', 'SIGIO', 'SIGIOT', 'SIGKILL', 'SIGPIPE', 'SIGPOLL', 'SIGPROF', 'SIGPWR', 'SIGQUIT', 'SIGRTMAX', 'SIGRTMIN', 'SIGSEGV', 'SIGSTOP', 'SIGSYS', 'SIGTERM', 'SIGTRAP', 'SIGTSTP', 'SIGTTIN', 'SIGTTOU', 'SIGURG', 'SIGUSR1', 'SIGUSR2', 'SIGVTALRM', 'SIGWINCH', 'SIGXCPU', 'SIGXFSZ', 'SIG_DFL', 'SIG_IGN', '__doc__', '__name__', 'alarm', 'default_int_handler', 'getsignal', 'pause', 'signal']


繫結訊號處理函式
#encoding:utf8
import os,signal
from time import sleep
def onsignal_term(a,b):
print 'SIGTERM'      # kill -15
signal.signal(signal.SIGTERM,onsignal_term)     # 接收訊號,執行相應函式


def onsignal_usr1(a,b):
print 'SIGUSR1'      # kill -10
signal.signal(signal.SIGUSR1,onsignal_usr1)


while 1:
print 'ID',os.getpid()
sleep(10)


通過另外一個程式傳送訊號
import os,signal
os.kill(16175,signal.SIGTERM)    # 傳送訊號,16175是繫結訊號處理函式的程式pid,需要自行修改
os.kill(16175,signal.SIGUSR1)


父程式接收子程式結束髮送的SIGCHLD訊號
#encoding:utf8
import os,signal
from time import sleep
  
def onsigchld(a,b):
print '收到子程式結束訊號'
signal.signal(signal.SIGCHLD,onsigchld)
  
pid = os.fork()                # 建立一個子程式,複製父程式所有資源操作
if pid == 0:                   # 通過判斷子程式os.fork()是否等於0,分別同時執行父程式與子程式操作
  print '我是子程式,pid是',os.getpid()
  sleep(2)
else:
print '我是父程式,pid是',os.getpid()
os.wait()      # 等待子程式結束


接收訊號的程式,另外一端使用多執行緒向這個程式傳送訊號,會遺漏一些訊號
#encoding:utf8
import os
import signal
from time import sleep  
import Queue
QCOUNT = Queue.Queue()  # 初始化佇列  
def onsigchld(a,b):  
'''收到訊號後向佇列中插入一個數字1'''
print '收到SIGUSR1訊號'
sleep(1)
QCOUNT.put(1)       # 向佇列中寫入
signal.signal(signal.SIGUSR1,onsigchld)   # 繫結訊號處理函式
while 1:
print '我的pid是',os.getpid()
print '現在佇列中元素的個數是',QCOUNT.qsize()
sleep(2)


多執行緒發訊號端的程式


#encoding:utf8
import threading
import os
import signal
def sendusr1():
print '傳送訊號'
os.kill(17788, signal.SIGUSR1)     # 這裡的程式id需要寫前一個程式實際執行的pid
WORKER = []
for i in range(1, 7):                  # 開啟6個執行緒
threadinstance = threading.Thread(target = sendusr1)
WORKER.append(threadinstance)  
for i in WORKER:
i.start()
for i in WORKER:
i.join()
print '主執行緒完成'


6 快取資料庫


python使用memcache


easy_install python-memcached   # 安裝(python2.7+)
import memcache
mc = memcache.Client(['10.152.14.85:12000'],debug=True)
mc.set('name','luo',60)
mc.get('name')
mc.delete('name1')

儲存資料


set(key,value,timeout)      # 把key對映到value,timeout指的是什麼時候這個對映失效
add(key,value,timeout)      # 僅當儲存空間中不存在鍵相同的資料時才儲存
replace(key,value,timeout)  # 僅當儲存空間中存在鍵相同的資料時才儲存


獲取資料


get(key)                    # 返回key所指向的value
get_multi(key1,key2,key3)   # 可以非同步地同時取得多個鍵值, 比迴圈呼叫get快數十倍


python使用mongodb


原文: http://blog.nosqlfan.com/html/2989.html

easy_install pymongo      # 安裝(python2.7+)
import pymongo
connection=pymongo.Connection('localhost',27017)   # 建立連線
db = connection.test_database                      # 切換資料庫
collection = db.test_collection                    # 獲取collection
# db和collection都是延時建立的,在新增Document時才真正建立


文件新增, _id自動建立
import datetime
post = {"author": "Mike",
"text": "My first blog post!",
"tags": ["mongodb", "python", "pymongo"],
"date": datetime.datetime.utcnow()}
posts = db.posts
posts.insert(post)
ObjectId('...')


批量插入
new_posts = [{"author": "Mike",
"text": "Another post!",
"tags": ["bulk", "insert"],
"date": datetime.datetime(2009, 11, 12, 11, 14)},
{"author": "Eliot",
"title": "MongoDB is fun",
"text": "and pretty easy too!",
"date": datetime.datetime(2009, 11, 10, 10, 45)}]
posts.insert(new_posts)
[ObjectId('...'), ObjectId('...')]

獲取所有collection
db.collection_names()    # 相當於SQL的show tables

獲取單個文件
posts.find_one()


查詢多個文件
for post in posts.find():
post


加條件的查詢
posts.find_one({"author": "Mike"})


高階查詢
posts.find({"date": {"$lt": "d"}}).sort("author")


統計數量
posts.count()


加索引
from pymongo import ASCENDING, DESCENDING
posts.create_index([("date", DESCENDING), ("author", ASCENDING)])


檢視查詢語句的效能
posts.find({"date": {"$lt": "d"}}).sort("author").explain()["cursor"]
posts.find({"date": {"$lt": "d"}}).sort("author").explain()["nscanned"]


python使用redis


https://pypi.python.org/pypi/redis
pip install redis  OR easy_install redis
import redis
r = redis.StrictRedis(host='localhost', port=6379, db=0)
r.set('foo', 'bar')
r.get('foo')
r.save()

分片 # 沒搞懂
redis.connection.Connection(host='localhost', port=6379, db=0,  parser_class=<class 'redis.connection.PythonParser'>)
redis.ConnectionPool( connection_class=<class 'redis.connection.Connection'>, max_connections=None, **connection_kwargs)


python使用kestrel佇列


# pykestrel
import kestrel


q = kestrel.Client(servers=['127.0.0.1:22133'],queue='test_queue') 
q.add('some test job') 
job = q.get()    # 從佇列讀取工作
job = q.peek()   # 讀取下一份工作
# 讀取一組工作
while True:
job = q.next(timeout=10) # 完成工作並獲取下一個工作,如果沒有工作,則等待10秒
if job is not None:
try:
# 流程工作
except:
q.abort() # 標記失敗工作


q.finish()  # 完成最後工作
q.close()   # 關閉連線

kestrel狀態檢查
# kestrel支援memcache協議客戶端
#!/usr/local/bin/python
# 10.13.81.125 22133  10000


import memcache
import sys
import traceback


ip="%s:%s" % (sys.argv[1],sys.argv[2])
try:
mc = memcache.Client([ip,])
st=mc.get_stats()
except:
print "kestrel connection exception"
sys.exit(2)


if st:
for s in st[0][1].keys():
if s.startswith('queue_') and s.endswith('_mem_items'):
num = int(st[0][1][s])
if num > int(sys.argv[3]):
print "%s block to %s" %(s[6:-6],num)
sys.exit(2)
print "kestrel ok!"
sys.exit(0)
else:
print "kestrel down"
sys.exit(2)


python使用tarantool


# pip install tarantool-queue


from tarantool_queue import Queue
queue = Queue("localhost", 33013, 0)     # 連線讀寫埠 空間0
tube = queue.tube("name_of_tube")        # 
tube.put([1, 2, 3])


task = tube.take()
task.data     # take task and read data from it
task.ack()    # move this task into state DONE


7 web頁面操作


urllib2        [網路資源訪問]


import urllib2
response = urllib2.urlopen('http://baidu.com')
print response.geturl()       # url
headers = response.info()
print headers                 # web頁面頭部資訊
print headers['date']         # 頭部資訊中的時間
date = response.read()        # 返回頁面所有資訊[字串]
# date = response.readlines() # 返回頁面所有資訊[列表]

for i in urllib2.urlopen('http://qq.com'):    # 可直接迭代
print i,


下載檔案


#!/usr/bin/env python
#encoding:utf8
import urllib2


url = 'http://www.01happy.com/wp-content/uploads/2012/09/bg.png'
file("./pic/%04d.png" % i, "wb").write(urllib2.urlopen(url).read())

抓取網頁解析指定內容


#!/usr/bin/env python
#encoding:utf8


import urllib2
import urllib
import random
from bs4 import BeautifulSoup


url='http://www.aaammm.com/aaa/'


ua=["Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)",
"Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1)",
"Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; InfoPath.2; .NET4.0C; .NET4.0E)",
"Mozilla/5.0 (Macintosh; Intel Mac OS X 10_7_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/36.0.1985.125 Safari/537.36",
"Mozilla/5.0 (Macintosh; Intel Mac OS X 10_7_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/36.0.1985.125 Safari/537.36",
"Mozilla/5.0 (Macintosh; Intel Mac OS X 10_7_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/36.0.1985.125 Safari/537.36",
"Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/36.0.1985.143 Safari/537.36",
"Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/37.0.2062.120 Safari/537.36",
"Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/37.0.2062.120 Safari/537.36",
"Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/37.0.2062.120 Safari/537.36",
"Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/37.0.2062.120 Safari/537.36",
"Mozilla/5.0 (Windows NT 6.1; WOW64; rv:31.0) Gecko/20100101 Firefox/31.0",
"Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/36.0.1985.143 Safari/537.36"]


browser = random.choice(ua)


req_header = {'User-Agent':browser,
'Accept':'text/html;q=0.9,*/*;q=0.8',
'Cookie':'BAIDUID=4C8274B52CFB79DEB4FBA9A7EC76A1BC:FG=1; BDUSS=1dCdU1WNFdxUll0R09XcnBZTkRrVVVNbWVnSkRKSVRPeVljOUswclBoLUNzVEpVQVFBQUFBJCQAAAAAAAAAAAEAAADEuZ8BcXVhbnpob3U3MjIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAIIIkC1SCJAtUY; BD_UPN=123143; BD_HOME=1',    # 添真實登陸後的Cookie 
'Accept-Charset':'ISO-8859-1,utf-8;q=0.7,*;q=0.3',
'Connection':'close',
}
#data = urllib.urlencode({'name':'xuesong','id':'30' })          # urllib 的處理引數的方法,可以再urllib2中使用
data = urllib2.quote("pgv_ref=im.perinfo.perinfo.icon&rrr=pppp") 
req_timeout = 10
try:
req = urllib2.Request(url,data=data,headers=req_header)      # data為None 則方法為get,有date為post方法
html = urllib2.urlopen(req,data=None,req_timeout).read()
except urllib2.HTTPError as err:
print str(err)
except:
print "timeout"
print(html)


# 百度帶Cookie後檢視自己的使用者
#for i in html.split('\n'):
# if 'bds.comm.user=' in i:
# print i

soup = BeautifulSoup(html)
for i in  soup.find_all(target="_blank",attrs={"class": "usr-pic"}):   # 條件看情況選擇
if i.img:
print(i.get('href'))


模擬瀏覽器訪問web頁面 python3
#! /usr/bin/env python
# -*- coding=utf-8 -*- 
import urllib.request


url = "http://www.baidu.com"
# AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.64 Safari/537.11
headers = {'User-Agent':'Mozilla/5.0 (Windows NT 6.1)',
'Accept':'text/html;q=0.9,*/*;q=0.8',
'Accept-Charset':'ISO-8859-1,utf-8;q=0.7,*;q=0.3',
'Connection':'close',
'Referer':None #注意如果依然不能抓取的話,這裡可以設定抓取網站的host
}


opener = urllib.request.build_opener()
opener.addheaders = [headers]
data = opener.open(url).read()


print(data)

requests       [替代urllib2]


# Requests是一個Python的HTTP客戶端庫
# 官方中文文件 http://cn.python-requests.org/zh_CN/latest/user/quickstart.html#id2
# 安裝: sudo pip install requests
import requests


# get方法提交表單
url = r'http://dict.youdao.com/search?le=eng&q={0}'.format(word.strip())
r = requests.get(url,timeout=2)

# get方法帶引數 http://httpbin.org/get?key=val
payload = {'key1': 'value1', 'key2': 'value2'}    
r = requests.get("http://httpbin.org/get", params=payload)  

# post方法提交表單
QueryAdd='http://www.anti-spam.org.cn/Rbl/Query/Result'
r = requests.post(url=QueryAdd, data={'IP':'211.211.54.54'})        

# 定製請求頭post請求
payload = {'some': 'data'}
headers = {'content-type': 'application/json'}
r = requests.post(url, data=json.dumps(payload), headers=headers)


# https 需登入加auth
r = requests.get('https://baidu.com', auth=('user', 'pass'))


if r.ok:    # 判斷請求是否正常
print r.url             # u'http://httpbin.org/get?key2=value2&key1=value1'
print r.status_code     # 狀態碼 
print r.content         # 獲取到的原始內容  可使用 BeautifulSoup4 解析處理判定結果
print r.text            # 把原始內容轉unicode編碼
print r.headers         # 響應頭
print r.headers['content-type']          # 網頁頭資訊 不存在為None
print r.cookies['example_cookie_name']   # 檢視cookie
print r.history         # 追蹤重定向 [<Response [301]>]  開啟重定向 allow_redirects=True  

獲取JSON
r = requests.get('https://github.com/timeline.json')
r.json()

獲取圖片
from PIL import Image
from StringIO import StringIO
i = Image.open(StringIO(r.content))


傳送cookies到伺服器
url = 'http://httpbin.org/cookies'
cookies = dict(cookies_are='working')
r = requests.get(url, cookies=cookies)
r.text         '{"cookies": {"cookies_are": "working"}}'


在同一個Session例項發出的所有請求之間保持cookies
s = requests.Session()
s.get('http://httpbin.org/cookies/set/sessioncookie/123456789')
r = s.get("http://httpbin.org/cookies")
print r.text

會話物件能夠跨請求保持某些引數
s = requests.Session()
s.auth = ('user', 'pass')
s.headers.update({'x-test': 'true'})
s.get('http://httpbin.org/headers', headers={'x-test2': 'true'})  # both 'x-test' and 'x-test2' are sent

ssl證照驗證
requests.get('https://github.com', verify=True)
requests.get('https://kennethreitz.com', verify=False)   # 忽略證照驗證
requests.get('https://kennethreitz.com', cert=('/path/server.crt', '/path/key'))   # 本地指定一個證照 正確 <Response [200]>  錯誤 SSLError


流式上傳
with open('massive-body') as f:
requests.post('http://some.url/streamed', data=f)


流式請求
import requests
import json


r = requests.post('https://stream.twitter.com/1/statuses/filter.json',
data={'track': 'requests'}, auth=('username', 'password'), stream=True)


for line in r.iter_lines():
if line: # filter out keep-alive new lines
print json.loads(line)

自定義身份驗證
from requests.auth import AuthBase
class PizzaAuth(AuthBase):
"""Attaches HTTP Pizza Authentication to the given Request object."""
def __init__(self, username):
# setup any auth-related data here
self.username = username
def __call__(self, r):
# modify and return the request
r.headers['X-Pizza'] = self.username
return r
requests.get('http://pizzabin.org/admin', auth=PizzaAuth('kenneth'))

基本身份認證
from requests.auth import HTTPBasicAuth
requests.get('https://api.github.com/user', auth=HTTPBasicAuth('user', 'pass')) 

摘要式身份認證
from requests.auth import HTTPDigestAuth            
url = 'http://httpbin.org/digest-auth/auth/user/pass'
requests.get(url, auth=HTTPDigestAuth('user', 'pass')) 

代理
import requests
proxies = {
 "http": "http://10.10.1.10:3128",
 # "http": "http://user:pass@10.10.1.10:3128/",  # 使用者名稱密碼
 "https": "http://10.10.1.10:1080",
}
requests.get("http://example.org", proxies=proxies)
#也可以設定環境變數之間訪問
export HTTP_PROXY="http://10.10.1.10:3128"
export HTTPS_PROXY="http://10.10.1.10:1080"


BeautifulSoup  [html\xml解析器]


# BeautifulSoup中文官方文件
# http://www.crummy.com/software/BeautifulSoup/bs3/documentation.zh.html
# http://www.crummy.com/software/BeautifulSoup/bs4/doc/index.zh.html
# Beautiful Soup將複雜HTML文件轉換成一個複雜的樹形結構,每個節點都是Python物件,所有物件可以歸納為4種: Tag , NavigableString , BeautifulSoup , Comment

匯入模組
from BeautifulSoup import BeautifulSoup          # For processing HTML  版本3.0 已停止更新
from BeautifulSoup import BeautifulStoneSoup     # For processing XML
import BeautifulSoup                             # To get everything
from bs4 import BeautifulSoup                    # 版本4.0 bs4 安裝: pip install BeautifulSoup4


from bs4 import BeautifulSoup
soup = BeautifulSoup(html_doc)    # 解析html文字 可以是 requests 提交返回的頁面 results.content
print(soup.prettify())            # 輸出解析後的結構
print(soup.title)                 # 指定標籤內容
print(soup.title.name)            # 標籤名
print(soup.title.string)          # 標籤內容
print(soup.title.parent.name)     # 上層標籤名
print(soup.p)                     # <p class="title"><b>The Dormouse's story</b></p>
print(soup.p['class'])            # u'title'  class屬性值
print(soup.a)                     # 找到第一個a標籤的標籤行
print(soup.find_all('a',limit=2)) # 找到a標籤的行,最多為limit個
print(soup.find(id="link3"))      # 標籤內id為link3的標籤行
print(soup.get_text())            # 從文件中獲取所有文字內容
soup.find_all("a", text="Elsie")  # 從文件中搜尋關鍵字
soup.find(text=re.compile("sisters"))  # 從文件中正則搜尋關鍵字
soup.find_all("a", class_="sister")    # 按CSS搜尋
soup.find_all(id='link2',"table",attrs={"class": "status"},href=re.compile("elsie"))   # 搜尋方法    
for i in  soup.find_all('a',attrs={"class": "usr-pic"}):    # 迴圈所有a標籤的標籤行
if i.a.img:
print(i.a.img.get("src"))                   # 取出當前a標籤中的連線
Tag
# find_all 後迴圈的值是 Tag 不是字串 不能直接擷取
tag.text                     # 文字
tag.name
tag.name = "blockquote"      # 查詢name為 blockquote 的
tag['class']
tag.attrs                    # 按熟悉查詢
tag['class'] = 'verybold'


del tag['class']             # 刪除
print(tag.get('class'))      # 列印屬性值
print(i.get('href'))         # 列印連線


json


#!/usr/bin/python
import json


#json file temp.json
#{ "name":"00_sample_case1", "description":"an example."}


f = file("temp.json");
s = json.load(f)        # 直接讀取json檔案
print s
f.close


d = {"a":1}
j=json.dumps(d)  # 字典轉json
json.loads(j)    # json轉字典

s = json.loads('{"name":"test", "type":{"name":"seq", "parameter":["1", "2"]}}')
print type(s)    # dic
print s
print s.keys()
print s["type"]["parameter"][1]


cookielib      [保留cookie登入頁面]


ck = cookielib.CookieJar()   # 通過 這個就可以實現請求帶過去的COOKIE與傳送回來的COOKIE值了。
opener = urllib2.build_opener(urllib2.HTTPCookieProcessor(ck))   # 獲取到COOKIE
urllib2.install_opener(opener)   # 此句設定urllib2的全域性opener
content = urllib2.urlopen(url).read()  

登入cacti取圖片
#encoding:utf8
import urllib2
import urllib
import cookielib
def renrenBrower(url,user,password):
#查詢form標籤中的action提交地址
login_page = "http://10.10.76.79:81/cacti/index.php"
try:
#獲得一個cookieJar例項
cj = cookielib.CookieJar()
#cookieJar作為引數,獲得一個opener的例項
opener=urllib2.build_opener(urllib2.HTTPCookieProcessor(cj))
#偽裝成一個正常的瀏覽器,避免有些web伺服器拒絕訪問
opener.addheaders = [('User-agent','Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1)')]
#生成Post資料,含有登陸使用者名稱密碼,所有表單內的input中name值
data = urllib.urlencode({"action":"login","login_username":user,"login_password":password})
#以post的方法訪問登陸頁面,訪問之後cookieJar會自定儲存cookie
opener.open(login_page,data)
#以帶cookie的方式訪問頁面
op=opener.open(url)
#讀取頁面原始碼
data=op.read()
#將圖片寫到本地
#file("1d.png" , "wb").write(data)
return data
except Exception,e:
print str(e)
print renrenBrower("http://10.10.76.79:81/cacti/graph_image.php?local_graph_id=1630&rra_id=0&view_type=tree&graph_start=1397525517&graph_end=1397611917","admin","admin")


例子2
import urllib, urllib2, cookielib  
import os, time  
 
headers = []  
 
def login():  
cj = cookielib.CookieJar()  
opener = urllib2.build_opener(urllib2.HTTPCookieProcessor(cj))  
login_url = r'http://zhixing.bjtu.edu.cn/member.php?mod=logging&action=login&loginsubmit=yes&infloat=yes&lssubmit=yes&inajax=1'  
login_data = urllib.urlencode({'cookietime': '2592000', 'handlekey': 'ls', 'password': 'xxx',  
'quickforward': 'yes', 'username': 'GuoYuan'})  
opener.addheaders = [('Host', 'zhixing.bjtu.edu.cn'),  
  ('User-Agent', 'Mozilla/5.0 (Ubuntu; X11; Linux i686; rv:8.0) Gecko/20100101 Firefox/8.0'),  
  ('Accept', 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8'),  
  ('Accept-Language', 'en-us,en;q=0.5'),  
  ('Accept-Encoding', 'gzip, deflate'),  
  ('Accept-Charset', 'ISO-8859-1,utf-8;q=0.7,*;q=0.7'),  
  ('Connection', 'keep-alive'),  
  ('Referer', 'http://zhixing.bjtu.edu.cn/forum.php'),]  
opener.open(login_url, login_data)  
return opener  
 
if __name__ == '__main__':  
opener = login()  
 
url = r'http://zhixing.bjtu.edu.cn/forum.php?mod=topicadmin&action=moderate&optgroup=2&modsubmit=yes&infloat=yes&inajax=1'      
data = {'fid': '601', 'formhash': '0cdd1596', 'frommodcp': '', 'handlekey': 'mods',  
'listextra': 'page%3D62', 'moderate[]': '496146', 'operations[]': 'type', 'reason': '...',  
'redirect': r'http://zhixing.bjtu.edu.cn/thread-496146-1-1.html', 'typeid': '779'}  
data2 = [(k, v) for k,v in data.iteritems()]  
 
cnt = 0  
for tid in range(493022, 496146 + 1):  
cnt += 1  
if cnt % 20 == 0: print  
print tid,  
 
data2.append(('moderate[]', str(tid)))  
if cnt % 40 == 0 or cnt == 496146:  
request = urllib2.Request(url=url, data=urllib.urlencode(data2))  
print opener.open(request).read()  
data2 = [(k, v) for k,v in data.iteritems()]  


httplib        [http協議的客戶端]


import httplib
conn3 = httplib.HTTPConnection('www.baidu.com',80,True,10) 


檢視網頁圖片尺寸型別

#將圖片讀入記憶體
#!/usr/bin/env python
#encoding=utf-8
import cStringIO, urllib2, Image
url = 'http://www.01happy.com/wp-content/uploads/2012/09/bg.png'
file = urllib2.urlopen(url)
tmpIm = cStringIO.StringIO(file.read())
im = Image.open(tmpIm)
print im.format, im.size, im.mode

爬蟲

#!/usr/bin/env python
#encoding:utf-8
#sudo pip install BeautifulSoup


import requests
from BeautifulSoup import BeautifulSoup
import re


baseurl = 'http://blog.sina.com.cn/s/articlelist_1191258123_0_1.html'


r = requests.get(baseurl)


for url in re.findall('<a.*?</a>', r.content, re.S):
if url.startswith('<a title='):
with open(r'd:/final.txt', 'ab') as f:
f.write(url + '\n')


linkfile = open(r'd:/final.txt', 'rb')
soup = BeautifulSoup(linkfile)
for link in soup.findAll('a'):
#print link.get('title') + ':    ' + link.get('href')
ss = requests.get(link.get('href'))
for content in re.findall('<div id="sina_keyword_ad_area2" class="articalContent  ">.*?</div>', ss.content, re.S):
with open(r'd:/myftp/%s.txt'%link.get('title').strip('<>'), 'wb') as f:
f.write(content)
print '%s   has been copied.' % link.get('title')


反垃圾郵件提交申訴


#很遺憾,反垃圾郵件聯盟改版後加了驗證碼

#!/usr/bin/env python
#encoding:utf-8
import requests
import re

IpList=['113.212.91.25','113.212.91.23']
QueryAdd='http://www.anti-spam.org.cn/Rbl/Query/Result'
ComplaintAdd='http://www.anti-spam.org.cn/Rbl/Getout/Submit'
data = {
'CONTENT':'''我們是一家正規的XXX。xxxxxxx。懇請將我們的傳送伺服器IP移出黑名單。謝謝!
處理措施:
1.XXXX。
2.XXXX。''',
'CORP':'abc.com',
'WWW':'www.abc.cm',
'NAME':'def',
'MAIL':'def@163.com.cn',
'TEL':'010-50000000',
'LEVEL':'0',
}


for Ip in IpList:
query = requests.post(url=QueryAdd, data={'IP':Ip})                   # 黑名單查詢
if query.ok:
if re.findall(u'\u7533\u8bc9\u8131\u79bb', query.text, re.S):     # 查詢關鍵字 申訴脫離 既表明在黑名單中
data['IP']=Ip
complaint = requests.post(url=ComplaintAdd, data=data)        # 提交申訴
if complaint.ok:
if re.findall(u'\u60a8\u7684\u9ed1\u540d\u5355\u8131\u79bb\u7533\u8bf7\u5df2\u63d0\u4ea4', complaint.text, re.S):
status='申請提交'
elif re.findall(u'\u8131\u79bb\u7533\u8bf7\u5df2\u88ab\u4ed6\u4eba\u63d0\u4ea4', complaint.text, re.S):
status='重複提交'
elif re.findall(u'\u7533\u8bf7\u7531\u4e8e\u8fd1\u671f\u5185\u6709\u88ab\u62d2\u7edd\u7684\u8bb0\u5f55', complaint.text, re.S):
status='近期拒絕'
else:
status='異常'
else:
status='正常'
print '%s  %s' %(Ip,status)


有道詞典


#!/usr/bin/env python
import requests
from bs4 import BeautifulSoup
# bs4安裝: pip install BeautifulSoup4


def youdao(word):
url = r'http://dict.youdao.com/search?le=eng&q={0}'.format(word.strip())
r = requests.get(url)
if r.ok:
soup = BeautifulSoup(r.content)
div = soup.find_all('div', class_='trans-container')[:1]    # find_all是bs4的方法
ul = BeautifulSoup(str(div[0]))
li = ul.find_all('li')
for mean in li:
print mean.text


def query():
print('Created by @littlepy, QQ:185635687')
while True:
word = raw_input('>>>')
youdao(word)


if __name__ == '__main__':
query()


python啟動http服務提供訪問或下載


python -m SimpleHTTPServer  9900


8 併發


#執行緒安全/競爭條件,鎖/死鎖檢測,同步/非同步,阻塞/非阻塞,epoll非阻塞IO,訊號量/事件,執行緒池,生產消費模型,偽併發,微執行緒,協程
#Stackless Python 是Python程式語言的一個增強版本,它使程式設計師從基於執行緒的程式設計方式中獲得好處,並避免傳統執行緒所帶來的效能與複雜度問題。Stackless為 Python帶來的微執行緒擴充套件,是一種低開銷、輕量級的便利工具


threading多執行緒


thread
start_new_thread(function,args kwargs=None)    # 產生一個新的執行緒
allocate_lock()                                # 分配一個LockType型別的鎖物件
exit()                                         # 讓執行緒退出
acquire(wait=None)                             # 嘗試獲取鎖物件
locked()                                       # 如果獲取了鎖物件返回True
release()                                      # 釋放鎖


thread例子


#!/usr/bin/env python
#thread_test.py
#不支援守護程式
import thread
from time import sleep,ctime


loops = [4,2]


def loop(nloop,nsec,lock):
print 'start loop %s at:%s' % (nloop,ctime())
sleep(nsec)
print 'loop %s done at: %s' % (nloop, ctime())
lock.release()              # 分配已獲得的鎖,操作結束後釋放相應的鎖通知主執行緒


def main():
print 'starting at:',ctime()
locks = []
nloops = range(len(loops))

for i in nloops:
lock = thread.allocate_lock()     # 建立一個鎖
lock.acquire()                    # 呼叫各個鎖的acquire()函式獲得鎖
locks.append(lock)                # 把鎖放到鎖列表locks中
for i in nloops:
thread.start_new_thread(loop,(i,loops[i],locks[i]))   # 建立執行緒
for i in nloops:
while locks[i].locked():pass      # 等待全部解鎖才繼續執行
print 'all DONE at:',ctime()


if __name__ == '__main__':
main()


thread例子1


#coding=utf-8
import thread,time,os


def f(name):
i =3
while i:
time.sleep(1)
print name
i -= 1
# os._exit()   會把整個程式關閉
os._exit(22)


if __name__ == '__main__':
thread.start_new_thread(f,("th1",))
while 1:
pass
os._exit(0)

threading
Thread                   # 表示一個執行緒的執行的物件
start()              # 開始執行緒的執行
run()                # 定義執行緒的功能的函式(一般會被子類重寫)
join(timeout=None)   # 允許主執行緒等待執行緒結束,程式掛起,直到執行緒結束;如果給了timeout,則最多等待timeout秒.
getName()            # 返回執行緒的名字
setName(name)        # 設定執行緒的名字
isAlive()            # 布林標誌,表示這個執行緒是否還在執行中
isDaemon()           # 返回執行緒的daemon標誌
setDaemon(daemonic)  # 後臺執行緒,把執行緒的daemon標誌設定為daemonic(一定要在呼叫start()函式前呼叫)
# 預設主執行緒在退出時會等待所有子執行緒的結束。如果希望主執行緒不等待子執行緒,而是在退出時自動結束所有的子執行緒,就需要設定子執行緒為後臺執行緒(daemon)
Lock              # 鎖原語物件
Rlock             # 可重入鎖物件.使單執行緒可以在此獲得已獲得了的鎖(遞迴鎖定)
Condition         # 條件變數物件能讓一個執行緒停下來,等待其他執行緒滿足了某個條件.如狀態改變或值的改變
Event             # 通用的條件變數.多個執行緒可以等待某個事件的發生,在事件發生後,所有的執行緒都會被啟用
Semaphore         # 為等待鎖的執行緒提供一個類似等候室的結構
BoundedSemaphore  # 與Semaphore類似,只是不允許超過初始值
Time              # 與Thread相似,只是他要等待一段時間後才開始執行
activeCount()     # 當前活動的執行緒物件的數量
currentThread()   # 返回當前執行緒物件
enumerate()       # 返回當前活動執行緒的列表
settrace(func)    # 為所有執行緒設定一個跟蹤函式
setprofile(func)  # 為所有執行緒設定一個profile函式


threading例子1

#!/usr/bin/env python
#encoding:utf8
import threading
from Queue import Queue
from time import sleep,ctime


class ThreadFunc(object):
def __init__(self,func,args,name=''):
self.name=name
self.func=func                    # loop
self.args=args                    # (i,iplist[i],queue)
def __call__(self):
apply(self.func,self.args)        # 函式apply() 執行loop函式並傳遞元組引數
def loop(nloop,ip,queue):
print 'start',nloop,'at:',ctime()
queue.put(ip)
sleep(2)
print 'loop',nloop,'done at:',ctime()
if __name__ == '__main__':
threads = []
queue = Queue()
iplist = ['192.168.1.2','192.168.1.3','192.168.1.4','192.168.1.5','192.168.1.6','192.168.1.7','192.168.1.8']
nloops = range(len(iplist))


for i in nloops:
t = threading.Thread(target=ThreadFunc(loop,(i,iplist[i],queue),loop.__name__))
threads.append(t)
for i in nloops:
threads[i].start()
for i in nloops:
threads[i].join()
for i in nloops:
print queue.get()


threading例子2


#!/usr/bin/env python
#encoding:utf8
from Queue import Queue
import random,time,threading

class Producer(threading.Thread):
def __init__(self, t_name, queue):
threading.Thread.__init__(self, name=t_name)
self.data=queue
def run(self):
for i in range(5):
print "%s: %s is producing %d to the queue!\n" %(time.ctime(), self.getName(), i)
self.data.put(i)
self.data.put(i*i)
time.sleep(2)
print "%s: %s finished!" %(time.ctime(), self.getName())


class Consumer(threading.Thread):
def __init__(self, t_name, queue):
threading.Thread.__init__(self, name=t_name)
self.data=queue
def run(self):
for i in range(10):
val = self.data.get()
print "%s: %s is consuming. %d in the queue is consumed!\n" %(time.ctime(), self.getName(), val)
print "%s: %s finished!" %(time.ctime(), self.getName())


if __name__ == '__main__':
queue = Queue()
producer = Producer('Pro.', queue)
consumer = Consumer('Con.', queue)
producer.start()
consumer.start()
producer.join()
consumer.join()


threading例子3

# 啟動執行緒後自動執行 run函式其他不可以
import threading
import time


class Th(threading.Thread):
def __init__(self,name):
threading.Thread.__init__(self)
self.t_name=name
self.daemon = True     # 預設為false,讓主執行緒等待處理完成
def run(self):
time.sleep(1)
print "this is " + self.t_name


if __name__ == '__main__':
thread1 = Th("Th_1")
thread1.start()


threading例子4

import threading
import time
class Th(threading.Thread):
def __init__(self,thread_name):
threading.Thread.__init__(self)
self.setName(thread_name)
def run(self):
threadLock.acquire()
print self.getName()
for i in range(3):
time.sleep(1)
print str(i)
print self.getName() +  " is over"
threadLock.release()


if __name__ == '__main__':
threadLock = threading.Lock()
thread1 = Th("Th_1")
thread2 = Th("Th_2")
thread1.start()
thread2.start()


後臺執行緒


import threading
import time,random


class MyThread(threading.Thread):
def run(self):
wait_time=random.randrange(1,10)
print "%s will wait %d seconds" % (self.name, wait_time)
time.sleep(wait_time)
print "%s finished!" % self.name


if __name__=="__main__":
for i in range(5):
t = MyThread()
t.setDaemon(True)    # 設定為後臺執行緒,主執行緒完成時不等待子執行緒完成就結束
t.start()


threading控制最大併發_查詢日誌中IP資訊


#!/usr/bin/env python
#coding:utf-8
import urllib2
import json
import threading
import time


'''
by:某大牛
QQ:185635687
這個是多執行緒併發控制. 如果要改成多程式,只需把threading 換成 mulitprocessing.Process , 對, 就是換個名字而已.
'''


#獲取ip 及其出現次數
def ip_dic(file_obj, dic):
for i in file_obj:
if i:
ip=i.split('-')[0].strip()
if ip in dic.keys():
dic[ip]=dic[ip] + 1
else:
dic[ip]=1
return dic.iteritems()


#目標函式
def get_data(url, ipcounts):
data=urllib2.urlopen(url).read()
datadict=json.loads(data)
fdata = u"ip:%s---%s,%s,%s,%s,%s" %(datadict["data"]["ip"],ipcounts,datadict["data"]["country"],datadict["data"]["region"],datadict["data"]["city"],datadict["data"]["isp"])
print fdata


#多執行緒
def threads(iters):
thread_pool = []
for k in iters:
url = "http://ip.taobao.com/service/getIpInfo.php?ip="
ipcounts = k[1]
url = (url + k[0]).strip()
t = threading.Thread(target=get_data, args=(url, ipcounts))
thread_pool.append(t)
return thread_pool


#控制多執行緒
def startt(t_list, max,second):
l = len(t_list)
n = max
while l > 0:
if l > max:
nl = t_list[:max]
t_list = t_list[max:]
for t in nl:
t.start()
time.sleep(second)
for t in nl:
t.join()
print '*'*15,  str(n)+ ' ip has been queried'+'*'*15
n += max
l = len(t_list)
continue
elif l <= max:
nl = t_list
for t in nl:
t.start()
for t in nl:
t.join()
print '>>> Totally ' + str(n+l ) + ' ip has been queried'
l = 0


if __name__ =="__main__":
dic={}
with open('access.log') as file_obj:
it = ip_dic(file_obj, dic)
t_list= threads(it)
startt(t_list, 15, 1)


多執行緒取佇列

#!/usr/bin/python


import Queue
import threading
import time


exitFlag = 0


class myThread (threading.Thread):
def __init__(self, threadID, name, q):
threading.Thread.__init__(self)
self.threadID = threadID
self.name = name
self.q = q
def run(self):
print "Starting " + self.name
process_data(self.name, self.q)
print "Exiting " + self.name


def process_data(threadName, q):
while not exitFlag:      # 死迴圈等待
queueLock.acquire()
if not q.empty():    # 判斷佇列是否為空
data = q.get()
print "%s processing %s" % (threadName, data)
queueLock.release()
time.sleep(1)


threadList = ["Thread-1", "Thread-2", "Thread-3"]
nameList = ["One", "Two", "Three", "Four", "Five"]
queueLock = threading.Lock()     # 鎖與佇列並無任何關聯,其他執行緒也進行取鎖操作的時候就會檢查是否有被佔用,有就阻塞等待解鎖為止
workQueue = Queue.Queue(10)
threads = []
threadID = 1


# Create new threads
for tName in threadList:
thread = myThread(threadID, tName, workQueue)
thread.start()
threads.append(thread)
threadID += 1


# Fill the queue
queueLock.acquire()
for word in nameList:
workQueue.put(word)
queueLock.release()


# Wait for queue to empty
while not workQueue.empty():   # 死迴圈判斷佇列被處理完畢
pass


# Notify threads it's time to exit
exitFlag = 1


# Wait for all threads to complete
for t in threads:
t.join()
print "Exiting Main Thread"

Queue通用佇列


q=Queue(size)       # 建立大小size的Queue物件
qsize()             # 返回佇列的大小(返回時候,可能被其他程式修改,近似值)
empty()             # 如果佇列為空返回True,否則Fales
full()              # 如果佇列已滿返回True,否則Fales
put(item,block0)    # 把item放到佇列中,如果給了block(不為0),函式會一直阻塞到佇列中有空間為止
get(block=0)        # 從佇列中取一個物件,如果給了block(不為0),函式會一直阻塞到佇列中有物件為止
get_nowait          # 預設get阻塞,這個不阻塞


multiprocessing [多程式併發]


多執行緒

import urllib2
from multiprocessing.dummy import Pool as ThreadPool


urls=['http://www.baidu.com','http://www.sohu.com']


pool=ThreadPool(4)   # 執行緒池
results=pool.map(urllib2.urlopen,urls)
pool.close()
pool.join()


多程式併發


#!/usr/bin/env python
#encoding:utf8
from multiprocessing import Process
import time,os
def f(name):
time.sleep(1)
print 'hello ',name
print os.getppid()   # 取得父程式ID
print os.getpid()    # 取得程式ID
process_list = []


for i in range(10):
p = Process(target=f,args=(i,))
p.start()
process_list.append(p)
for j in process_list:
j.join()


Queue程式間通訊


from multiprocessing import Process,Queue
import time
def f(name):
time.sleep(1)
q.put(['hello'+str(name)])
process_list = []
q = Queue()
if __name__ == '__main__':
for i in range(10):
p = Process(target=f,args=(i,))
p.start()
process_list.append(p)
for j in process_list:
j.join()
for i in range(10):
print q.get()


Pipe管道

from multiprocessing import Process,Pipe
import time
import os


def f(conn,name):
time.sleep(1)
conn.send(['hello'+str(name)])
print os.getppid(),'-----------',os.getpid()
process_list = []
parent_conn,child_conn = Pipe()
if __name__ == '__main__':
for i in range(10):
p = Process(target=f,args=(child_conn,i))
p.start()
process_list.append(p)
for j in process_list:
j.join()
for p in range(10):
print parent_conn.recv()


程式間同步
#加鎖,使某一時刻只有一個程式 print
from multiprocessing import Process,Lock
import time
import os


def f(name):
lock.acquire()
time.sleep(1)
print 'hello--'+str(name)
print os.getppid(),'-----------',os.getpid()
lock.release()
process_list = []
lock = Lock()
if __name__ == '__main__':
for i in range(10):
p = Process(target=f,args=(i,))
p.start()
process_list.append(p)
for j in process_list:
j.join()


共享記憶體


# 通過使用Value或者Array把資料儲存在一個共享的記憶體表中
# 'd'和'i'引數是num和arr用來設定型別,d表示一個雙精浮點型別,i表示一個帶符號的整型。
from multiprocessing import Process,Value,Array
import time
import os


def f(n,a,name):
time.sleep(1)
n.value = name * name
for i in range(len(a)):
a[i] = -i
process_list = []
if __name__ == '__main__':
num = Value('d',0.0)
arr = Array('i',range(10))
for i in range(10):
p = Process(target=f,args=(num,arr,i))
p.start()
process_list.append(p)
for j in process_list:
j.join()
print num.value
print arr[:]


manager


# 比共享記憶體靈活,但緩慢
# 支援list,dict,Namespace,Lock,Semaphore,BoundedSemaphore,Condition,Event,Queue,Value,Array
from multiprocessing import Process,Manager
import time
import os


def f(d,name):
time.sleep(1)
d[name] = name * name
print d
process_list = []
if __name__ == '__main__':
manager = Manager()
d = manager.dict()
for i in range(10):
p = Process(target=f,args=(d,i))
p.start()
process_list.append(p)
for j in process_list:
j.join()
print d


最大併發數


import multiprocessing
import time,os


result = []
def run(h):
print 'threading:' ,h,os.getpid()
p = multiprocessing.Pool(processes=20)


for i in range(100):
result.append(p.apply_async(run,(i,)))
p.close()

for res in result:
res.get(timeout=5)


9 框架


flask    [微型網路開發框架]

# http://dormousehole.readthedocs.org/en/latest/
# html放在 ./templates/   js放在 ./static/

request.args.get('page', 1)          # 獲取引數 ?page=1
request.json                         # 獲取傳遞的整個json資料
request.form.get("host",'127')       # 獲取表單值

簡單例項 # 接收資料和展示


import MySQLdb as mysql
from flask import Flask, request


app = Flask(__name__)
db.autocommit(True)
c = db.cursor()


"""
CREATE TABLE `statusinfo` (
 `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
 `hostname` varchar(32) NOT NULL,
 `load` float(10) NOT NULL DEFAULT 0.00,
 `time` int(15) NOT NULL,
 `memtotal` int(15) NOT NULL,
 `memusage` int(15) NOT NULL,
 `memfree` int(15) NOT NULL,
 PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=161 DEFAULT CHARSET=utf8;
"""


@app.route("/collect", methods=["GET", "POST"])
def collect():
sql = ""
if request.method == "POST":
data = request.json                      # 獲取傳遞的json
hostname = data["Host"]
load = data["LoadAvg"]
time = data["Time"]
memtotal = data["MemTotal"]
memusage = data["MemUsage"]
memfree = data["MemFree"]

try:
sql = "INSERT INTO `statusinfo` (`hostname`,`load`,`time`,`memtotal`,`memusage`,`memfree`) VALUES('%s', %s, %s, %s, %s, %s);" % (hostname, load,time,memtotal,memusage,memfree)
ret = c.execute(sql)
return 'ok'
except mysql.IntegrityError:
return 'errer'


@app.route("/show", methods=["GET", "POST"])
def show():
try:
hostname = request.form.get("hostname")     # 獲取表單方式的變數值
sql = "SELECT `load` FROM `statusinfo` WHERE hostname = '%s';" % (hostname)
c.execute(sql)
ones = c.fetchall()
return render_template("sysstatus.html", data=ones, sql = sql)
except:
print 'hostname null'


from flask import render_template
@app.route("/xxx/<name>")
def hello_xx(name):
return render_template("sysstatus.html", name='teach')


if __name__ == "__main__":
app.run(host="0.0.0.0", port=50000, debug=True)


twisted  [非阻塞非同步伺服器框架]


# 用來進行網路服務和應用程式的程式設計。雖然 Twisted Matrix 中有大量鬆散耦合的模組化元件,但該框架的中心概念還是非阻塞非同步伺服器這一思想。對於習慣於執行緒技術或分叉伺服器的開發人員來說,這是一種新穎的程式設計風格,但它卻能在繁重負載的情況下帶來極高的效率。
pip install twisted

from twisted.internet import protocol, reactor, endpoints


class Echo(protocol.Protocol):
def dataReceived(self, data):
self.transport.write(data)
class EchoFactory(protocol.Factory):
def buildProtocol(self, addr):
return Echo()


endpoints.serverFromString(reactor, "tcp:1234").listen(EchoFactory())
reactor.run()


greenlet [微執行緒/協程框架]


# 更加原始的微執行緒的概念,沒有排程,或者叫做協程。這在你需要控制你的程式碼時很有用。你可以自己構造微執行緒的 排程器;也可以使用"greenlet"實現高階的控制流。例如可以重新建立構造器;不同於Python的構造器,我們的構造器可以巢狀的呼叫函式,而被巢狀的函式也可以 yield 一個值。
pip install greenlet


tornado  [極輕量級Web伺服器框架] 


# 高可伸縮性和epoll非阻塞IO,響應快速,可處理數千併發連線,特別適用用於實時的Web服務
# http://www.tornadoweb.cn/documentation
pip install tornado

import tornado.ioloop
import tornado.web


class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")


application = tornado.web.Application([
(r"/", MainHandler),
])


if __name__ == "__main__":
application.listen(8888)
tornado.ioloop.IOLoop.instance().start()


Scrapy   [web抓取框架]
# Python開發的一個快速,高層次的螢幕抓取和web抓取框架,用於抓取web站點並從頁面中提取結構化的資料。Scrapy用途廣泛,可以用於資料探勘、監測和自動化測試。
pip install scrapy

from scrapy import Spider, Item, Field


class Post(Item):
title = Field()


class BlogSpider(Spider):
name, start_urls = 'blogspider', ['http://blog.scrapinghub.com']


def parse(self, response):
return [Post(title=e.extract()) for e in response.css("h2 a::text")]

scrapy runspider myspider.py


django   [重量級web框架]


bottle   [輕量級的Web框架]


10 例子


小演算法


斐波那契
#將函式結果作為列表可用於迴圈
def fab(max): 
n, a, b = 0, 0, 1 
while n < max: 
yield b         
a, b = b, a + b 
n = n + 1 
for n in fab(5): 
print n


乘法口訣


#!/usr/bin/python
for i in range(1,10):
for j in range(1,i+1):
print j,'*',i,'=',j*i,
else:
print ''


最小公倍數


# 1-70的最小公倍數
def c(m,n):
a1=m
b1=n
r=n%m
while r!=0:
n=m
m=r
r=n%m
return (a1*b1)/m
d=1
for i in range(3,71,2):
d = c(d,i)
print d


排序演算法


插入排序
def insertion_sort(sort_list):
iter_len = len(sort_list)
if iter_len < 2:
return sort_list
for i in range(1, iter_len):
key = sort_list[i]
j = i - 1
while j>=0 and sort_list[j]>key:
sort_list[j+1] = sort_list[j]
j -= 1
sort_list[j+1] = key
return sort_list


選擇排序
def selection_sort(sort_list):
iter_len = len(sort_list)
if iter_len < 2:
return sort_list
for i in range(iter_len-1):
smallest = sort_list[i]
location = i
for j in range(i, iter_len):
if sort_list[j] < smallest:
smallest = sort_list[j]
location = j
if i != location:
sort_list[i], sort_list[location] = sort_list[location], sort_list[i]
return sort_list


氣泡排序演算法
def bubblesort(numbers):
for j in range(len(numbers)-1,-1,-1):
for i in range(j):
if numbers[i]>numbers[i+1]:
numbers[i],numbers[i+1] = numbers[i+1],numbers[i]
print(i,j)
print(numbers)


二分演算法


#python 2f.py 123456789 4
# list('123456789')  =  ['1', '2', '3', '4', '5', '6', '7', '8', '9']
#!/usr/bin/env python 
import sys


def search2(a,m):
low = 0
high = len(a) - 1
while(low <= high):
mid = (low + high)/2
midval = a[mid]


if midval < m:
low = mid + 1
elif midval > m:
high = mid - 1
else:
print mid
return mid
print -1
return -1


if __name__ == "__main__":
a = [int(i) for i in list(sys.argv[1])]
m = int(sys.argv[2])
search2(a,m)

將字典中所有time去掉

a={'version01': {'nba': {'timenba': 'valuesasdfasdf', 'nbanbac': 'vtimefasdf', 'userasdf': 'vtimasdf'}}}
eval(str(a).replace("time",""))

PIL影象處理


import Image
im = Image.open("j.jpg")            # 開啟圖片
print im.format, im.size, im.mode   # 列印影象格式、畫素寬和高、模式
# JPEG (440, 330) RGB
im.show()                           # 顯示最新載入影象
box = (100, 100, 200, 200)
region = im.crop(box)               # 從影象中提取出某個矩形大小的影象


圖片等比縮小


# -*- coding: cp936 -*-
import Image  
import glob, os  
 
#圖片批處理  
def timage():  
for files in glob.glob('D:\\1\\*.JPG'):  
filepath,filename = os.path.split(files)  
filterame,exts = os.path.splitext(filename)  
#輸出路徑  
opfile = r'D:\\22\\'  
#判斷opfile是否存在,不存在則建立  
if (os.path.isdir(opfile)==False):  
os.mkdir(opfile)  
im = Image.open(files)  
w,h = im.size  
#im_ss = im.resize((400,400))  
#im_ss = im.convert('P')  
im_ss = im.resize((int(w*0.12), int(h*0.12)))  
im_ss.save(opfile+filterame+'.jpg')  
 
if __name__=='__main__':  
timage()


取系統返回值賦給序列


cmd = os.popen("df -Ph|awk 'NR!=1{print $5}'").readlines();
cmd = os.popen('df -h').read().split('\n')
cmd = os.popen('lo 2>&1').read()

#取磁碟使用空間
import commands
df = commands.getoutput("df -hP")
[ x.split()[4] for x in df.split("\n") ] 
[ (x.split()[0],x.split()[4]) for x in df.split("\n") if x.split()[4].endswith("%") ] 


列印表格


map = [["a","b","c"],
  ["d","e","f"],
  ["g","h","i"]]
def print_board():
for i in range(0,3):
for j in range(0,3):
print "|",map[i][j],
#if j != 2:
print '|'


生成html檔案表格


log_file = file('check.html', 'w')
log_file.write("""
<!DOCTYPE HTML>
<html lang="utr-8">
<head>
<meta charset="UTF-8">
<title></title>
</head>
<body>
<table align='center' border='0' cellPadding='0'  style='font-size:24px;'><tr ><td>狀態統計</td></tr></table>
<style>.font{font-size:13px}</style>
<table  align='center' border='1' borderColor=gray cellPadding=3 width=1350  class='font'>
<tr style='background-color:#666666'>
 <th width=65>IP</th>
 <th width=65>狀態</th>
</tr>
""")
for i in list:
log_file.write('<tr><td>%s</td><td>%s</td></tr>\n' %(i.split()[0],i.split()[1]) )
log_file.write("""
</table>
</body>
</html>
""")
log_file.flush()
log_file.close()


井字遊戲


#!/usr/bin/python
# http://www.admin10000.com/document/2506.html
def print_board():
for i in range(0,3):
for j in range(0,3):
print map[2-i][j],
if j != 2:
print "|",
print ""
 
def check_done():
for i in range(0,3):
if map[i][0] == map[i][1] == map[i][2] != " " \
or map[0][i] == map[1][i] == map[2][i] != " ":
print turn, "won!!!"
return True
 
if map[0][0] == map[1][1] == map[2][2] != " " \
or map[0][2] == map[1][1] == map[2][0] != " ":
print turn, "won!!!"
return True
 
if " " not in map[0] and " " not in map[1] and " " not in map[2]:
print "Draw"
return True
 
return False
 
turn = "X"
map = [[" "," "," "],
  [" "," "," "],
  [" "," "," "]]
done = False
 
while done != True:
print_board()
 
print turn, "'s turn"
print
 
moved = False
while moved != True:
print "Please select position by typing in a number between 1 and 9, see below for which number that is which position..."
print "7|8|9"
print "4|5|6"
print "1|2|3"
print
 
try:
pos = input("Select: ")
if pos <=9 and pos >=1:
Y = pos/3
X = pos%3
if X != 0:
X -=1
else:
X = 2
Y -=1
 
if map[Y][X] == " ":
map[Y][X] = turn
moved = True
done = check_done()
 
if done == False:
if turn == "X":
turn = "O"
else:
turn = "X"
 
except:
print "You need to add a numeric value"


網段劃分


題目
192.168.1
192.168.3
192.168.2
172.16.3
192.16.1
192.16.2
192.16.3
10.0.4


輸出結果:
192.16.1-192.16.3
192.168.1-192.168.3
172.16.3
10.0.4


答案
#!/usr/bin/python


f = file('a.txt')
c = f.readlines()
dic={}


for i in c:
a=i.strip().split('.')
if a[0]+'.'+a[1] in dic.keys():
key=dic["%s.%s" %(a[0],a[1])]
else:
key=[]
key.append(a[2])
dic[a[0]+'.'+a[1]]=sorted(key)


for x,y in dic.items():
if y[0] == y[-1]:
print '%s.%s' %(x,y[0])
else:
print '%s.%s-%s.%s' %(x,y[0],x,y[-1])


統計日誌IP
# 列印出獨立IP,並統計獨立IP數
219.140.190.130 - - [23/May/2006:08:57:59 +0800] "GET /fg172.exe HTTP/1.1" 200 2350253
221.228.143.52 - - [23/May/2006:08:58:08 +0800] "GET /fg172.exe HTTP/1.1" 206 719996
221.228.143.52 - - [23/May/2006:08:58:08 +0800] "GET /fg172.exe HTTP/1.1" 206 713242


#!/usr/bin/python
dic={}
a=open("a").readlines()
for i in a:
ip=i.strip().split()[0]
if ip in dic.keys():
dic[ip] = dic[ip] + 1
else:
dic[ip] = 1
for x,y in dic.items():
print x," ",y






不定期更新,更新下載地址:
http://hi.baidu.com/quanzhou722/item/cf4471f8e23d3149932af2a7


請勿刪除資訊,植入廣告,抵制不道德行為。

相關文章