廖雪峰Python教程答案
阿新 • • 發佈:2018-12-10
課程地址:https://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000
感謝廖老師。
高階特性
生成器 generator
- 楊輝三角
楊輝三角定義如下:
把每一行看做一個list,試寫一個generator,不斷輸出下一行的list。
def Sanjiao(max): n = 1 if max == 0: print () elif max == 1: print (1) else: j = 1 L = [] while j <= max: L.append([1]*j) j = j +1 while n <= max-1: i = 1 while i < n : L[n][i]=(L[n-1][i]+L[n-1][i-1]) i = i+1 n = n +1 return L
def sanjiao(number): if number == 0: print() else: n =1 L, M =[[1],], [1] yield M while n < number : M = [1]+[(L[n-1][i]+L[n-1][i-1]) for i in range(1, n)]+[1] n = n +1 L.append(M) yield M return 'done'
函數語言程式設計
##map/reduce
- 利用map()函式,把使用者輸入的不規範的英文名字,變為首字母大寫,其他小寫的規範名字。輸入:[‘adam’, ‘LISA’, ‘barT’],輸出:[‘Adam’, ‘Lisa’, ‘Bart’]:
def standlize(name):
Name = ''
Name = Name + name[1].upper() + name[2:].lower()
return Name
- Python提供的sum()函式可以接受一個list並求和,請編寫一個prod()函式,可以接受一個list並利用reduce()求積:
def prod(l):
def prod_twonums(x,y):
return x*y
reduce(prod_twonums,l)
- 利用map和reduce編寫一個str2float函式,把字串’123.456’轉換成浮點數123.456:
def str2float(s):
def char2num(x):
DIGITS = {'0':0, '1':1, '2':2, '3':3, '4':4, '5':5, '6':6, '7':7, '8': 8, '9':9}
return DIGITS[x]
def fn1(x,y):
return x*10+y
def fn2(x,y):
return x*0.1+y
i =0
while s[i] != '.':
i = i+1
s1=s[:i]
s2=s[i+1:][::-1]
float1= reduce(fn1,map(char2num,s1))
float2 = reduce(fn2,map(char2num,s2))/10
return float1+float2
裝飾器
請設計一個decorator,它可作用於任何函式上,並列印該函式的執行時間:
# _*_ coding: utf-8 -*-
#
import functools
import time
def metric(func):
@functools.wraps(func)
def wrapper(*args, **kw):
start=time.clock()
s = func(*args)
elapsed = (time.clock() - start)
print('%s executed in %s ms' % (func.__name__, elapsed))
return s
return wrapper
@metric
def fast(x,y):
return x+y
@metric
def slow(x,y,z):
return x*y*z
IO程式設計
操作檔案與目錄
第一題:命令列裡dir -l的作用是:
第二題:編寫一個程式,能在當前目錄以及當前目錄的所有子目錄下查詢檔名包含指定字串的檔案,並列印相對路徑。
-
要注意遞迴函式的用法
-
在手動輸入路徑時,遇到這樣一個錯誤:
(unicode error) ‘unicodeescape’ codec can’t decode bytes in position 2-3: truncated \UXXXXXXXX escape
解決方法如下:unicode error -
拼接路徑一定要用os.path.join()這個函式
import os
l = []
def f2(s):
return lambda p: s in p
def f1(rootDir,s):
for x in os.listdir(rootDir):
p = os.path.join(rootDir,x)
l.append(p)
if os.path.isdir(x):
f1(p)
return filter(f2(s),l)
for i in f1(r'C:\Users\lones\Desktop\Test','Python'):
print(i)
程序與執行緒
多程序
正則表示式
第一題:
import re
re_emailaddr = re.compile(r'^(\w[a-zA-Z.]+)(@)(\w[a-z]+)(.com)$')
def is_valid_email(addr):
if re_emailaddr.match(addr):
return True
else:
print('%s is a wrong email addr' % addr)
if name == 'main':
assert is_valid_email('[email protected]')
assert is_valid_email('[email protected]')
assert not is_valid_email('bob#example.com')
assert not is_valid_email('[email protected]')
print('ok')
第二題:
import re
re_emailaddr = re.compile(r'^(.+)(@)(\w[a-z]+)(.\w{2,3})$')
def name_of_email(addr):
m = re_emailaddr.match(addr)
if m:
if '<' in m.group(1):
L = re.split(r'[>\<]',m.group(1))
return L[1]
else:
return m.group(1)
else:
print('%s is a wrong email addr' % addr)
if name == 'main':
assert name_of_email('<Tom Paris> [email protected]') == 'Tom Paris'
assert name_of_email('[email protected]') == 'tom'
print('ok')
常用內建模組
datetime
獲取使用者輸入的日期和時間如2015-1-21 9:01:30,以及一個時區資訊
如UTC+5:00,均是str,請編寫一個函式將其轉換為timestamp
-- coding:utf-8 --
import re
from datetime import datetime,timezone,timedelta
re_datetime = re.compile(r'^(\d{4})-(0[1-9]|1[0-2]|[1-9])-(0[1-9]|1[0-2]|2[0-9]|3[0-1]|[0-9])'
r'\s(0[0-9]|1[0-9]|2[0-3]|[0-9])'
r':(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])'
r':(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])$')
re_timezone = re.compile(r'^(UTC)(+|-)([0-9]|0[0-9]|1[0-2]):(00)$')
def to_timestamp(dt_str,tz_str):
m = re_datetime.match(dt_str)
n = re_timezone.match(tz_str)
if m and n:
cdatetime = datetime.strptime(dt_str, '%Y-%m-%d %H:%M:%S')
if(n[1] == '+'):
cdatetime = cdatetime + timedelta(hours = int(n[3]))
else:
cdatetime = cdatetime - timedelta(hours = int(n[3]))
return cdatetime.timestamp()
elif n and not m:
print('datetime is wrong')
elif not n and m:
print('timezone is wrong')
else:
print('both timezone and datetime are wrong')
t1 = to_timestamp('2015-6-1 08:10:30', 'UTC+7:00')
assert t1 == 1433121030.0
t2 = to_timestamp('2015-5-31 16:10:30', 'UTC-09:00')
assert t2 == 1433121030.0
print('ok')
struct
#-- coding:utf-8 --
import struct,base64
def bmp_info(data):
b = struct.unpack('<ccIIIIIIHH',data)
if b[0] == b'B' and b[1] == b'M':
return {'width':b[-4],'height':b[-3],'color':b[-1]}
else:
print('這不是一個位圖')
if name == 'main':
with open(r'C:\Users\lones\Desktop\Test-16位.bmp', 'rb') as f:
bmp_data = f.read(30)
bi = bmp_info(bmp_data)
assert bi['width'] == 1152
assert bi['height'] == 648
assert bi['color'] == 4
print('ok')
itertools
# -*- coding: utf-8 -*-
import itertools
def pi(N):
#'計算pi的值'
# step 1:建立一個奇數序列:1,3,5,7,9
odd = itertools.count(1, 2)
# step 2:取該序列的前N項: 1,3,5,7,9,......,2*N-1
oddn = itertools.takewhile(lambda x : x <= 2*N-1, odd)
# step 3:新增正負號並用4除
oddnlist = list(oddn) # 將iterator oddn轉換為一個list,否則計算oddn2的時候會有錯誤
oddn1 = map(lambda x : 4/x, filter(lambda x:(x+1)%4 !=0,oddnlist))
oddn2 = map(lambda x : -4/x, filter(lambda x:(x+1)%4 ==0,oddnlist))
return sum(oddn1)+sum(oddn2)
if __name__ == '__main__':
print(pi(10))
print(pi(100))
print(pi(1000))
print(pi(10000))
assert 3.04 < pi(10) < 3.05
assert 3.13 < pi(100) < 3.14
assert 3.140 < pi(1000) < 3.141
assert 3.1414 < pi(10000) < 3.1415
print('ok')
計算結果:
3.0418396189294024
3.131592903558553
3.1405926538397777
3.141492653590049
ok