## 簡介
### python是什么
> 編程語言,上手快功能強大,`模塊多`,`第三方模塊多`
> 模塊包括 `數據庫` `web` `文件處理`
### 優缺點
> 簡單,基礎庫,第三方庫多,提高`工作效率`
> 缺點,解釋型語言`效率不及` 編譯語言
### python應用場景
> 1 豆瓣等都是python開發
> 2 應用場景 `web開發` `自動化運維` `數據分析` `機器學習`
## Install&per
### Install
* win install
[python_install](https://www.python.org/downloads/)
* mac python installation via package manager
```
brew install python
```
### Text
`PyCharm`, a great advanced IDE. Students can get the license for free.
`Sublime`, awesome customizable text editor
`Atom`, similar to Sublime, developed by Github
`Vim`, advanced text editor, on a holy war with emacs
### Package manager
Python - `pip`
Java - `mvn`
JavaScript - `npm`
```
pip --version
pip install pytest
pip list
```
### Jupyter
> The Jupyter Notebook is an open-source web application that allows you to create and share documents that contain live code, equations, visualizations and narrative text. Uses include: data cleaning and transformation, numerical simulation, statistical modeling, data visualization, machine learning, and much more.
```
pip install jupyter
jupyter --version
#lunch
jupyter notebook
```
* 操作
```
# 新建
shift+enter
# 執行
control+enter
```
## 查看幫助文檔等
```
# 查看字符串對象幫助文檔
help(str)
# 查看字符串對象屬性和方法
dir(str)
# 查看字符串對象文檔
str?
```
## 變量
## 運算符
## 流程控制
### 條件控制
* 1 輸入一個數判斷和10之間的大小關系
* `>10`
* `<10`
* `==10`
```python
a = int(input("Please enter: "))
if a > 10:
print('a > 10')
elif a == 10:
print('a == 10')
else:
print('a < 10')
```
### 循環控制
* 2 for循環遍歷列表
```python
strlist = ['hello','viviwong','.com']
for s in strlist:
print(s)
```
* 3 for循環迭代數字列表 0-9
```python
for a in range(10):
print(a)
```
* 4 while循環遍歷100-10
```python
w = 100
while w > 10:
print(w)
w -= 10
```
## 異常處理
### 異常
> 不符合預期的用戶操作或數據輸入,程序會出現異常,處理異常保證程序穩定性
* 5 文件沒找到報異常
```python
filename = input("Enter file path:")
f = open(filename)
print(f.read())
```
* 常見異常
* `NameError`
* `SyntaxError`
* `IndexError`
* `KeyError`
* `ValueError`
* `AttributeError`
```python
`NameError` 未定義變量
`SyntaxError` 語法錯誤
`IndexError` 序列索引超過范圍
`KeyError` 字典key不存在
`ValueError` 傳入無效參數
`AttributeError` 對象屬性不存在
```
### 異常處理
* 異常處理代碼格式
```python
try:
可能拋異常的代碼
except: 異常類型名稱:
處理代碼
except: 異常類型名稱:
處理代碼
finally:
無論如何都執行的代碼
```
* 6 文件讀取異常處理
```python
filename = input("Enter file path:")
try:
f = open(filename)
print(f.read())
f.close()
except FileNotFoundError:
print("File not found")
finally:
print('我執行了')
```
## 模塊和包
> import引入`模塊` 模塊中的`函數` `類`到代碼中
* 7 python默認模塊搜索路徑,當前目錄及系統中python模塊的主要安裝目錄
```python
import sys
sys.path
```
* 模塊
* `模塊:` 每一個`x.py`都是一個`python模塊`
* `包:` 目錄`vivi`里面有一個`__init__.py`那么`vivi`文件夾就是一個包
* 導入包里面的模塊 導入模塊里面的方法
* 8 模塊導入
```python
from 包 import 模塊
from 模塊 import 方法
```
## __main__
* 9 作為模塊導入
```python
# 作為模塊導入
作為模塊導入
if __name__ == '__main__':
```
* 10 作為代碼執行
```python
作為模塊導入
if __name__ == '__main__':
pass
# 作為代碼執行
# 作為代碼執行
```
## 四種數據結構 list tuple set dict
### list
> 有序可修改
* 11 list
```
courses = ['Linux', 'Python', 'Vim', 'C++']
courses,type(courses)
courses[0]
courses.append('PHP')
```
### tuple
> 有序不可修改
* 12 tuple
```
courses = ('C++', 'Cloud', 'Linux', 'PHP')
courses,type(courses)
courses[0]
courses.append('PHP')
```
### set
> 無序不重復
* 13 set
```
courses = {'Linux', 'C++', 'Vim', 'Linux'}
courses,type(courses)
'Linux' in courses
```
### dict
> 無序的鍵值對
* 14 dict
```
coursesdict = {'class1':'Linux', 'class2':'Vim'}
courses,type(courses)
coursesdict['class1']
```
## function
* 15函數
```
def char_count(str, char):
return str.count(char)
result = char_count('hello viviwong','i')
```
## oop
* 抽象
* 封裝
* 繼承
* 多態
* 16 oop
```
class Animal(object):
def __init__(self, name):
self._name = name
def get_name(self):
return self._name
def set_name(self, value):
self._name = value
# 每個動物發出的聲音不一樣,pass直接略過
def make_sound(self):
pass
```
## 文件處理
> 文件處理解決的問題,數據`持久化`和獲取`配置`
* 17 file
```
filename = input('Enter the file name: ')
with open(filename) as file:
count = 0
for line in file:
count +=1
print(line)
print('Lines:',count)
```
## python高級特性
### 簡介
> python的有很多高級用法,可以極大的提高編程效率和代碼質量
## lambda
> 匿名函數 lambda
> 通常返回值不需要使用return
> 通常用在需要傳入`函數`作為參數的地方
> 并且函數只在這個地方使用,
> 匿名函數作為`參數`傳遞進去
* 18 匿名函數
* 定義匿名函數實現倍增
* 使用匿名函數
```python
# 定義匿名函數
double =lambda x: x*2
# 使用匿名函數
double(5)
```
## 切片slice
> 獲取序列 (list tuple)或字符串的一部分
> 切片格式 `序列[起始index:結束index]`
* 19 列表切片
* 定義列表
* 切片截取部分正切 負切 全部
```python
# 正切
letters = ['a', 'b', 'c', 'd', 'e', 'f', 'g']
letters[1:3]
# 下標對應關系
0 1 2 3 4 5 6
a b c d e f g
-7 -6 -5 -4 -3 -2 -1
# 負切
letters = ['a', 'b', 'c', 'd', 'e', 'f', 'g']
letters[1:-4]
letters[:4]
letters[4:]
# 復制
copy = letters[:]
```
## 列表解析list comprehension
> 列表解析(列表推導),優雅的方式操作列表元素
* 20 列表解析
* 列表1-10
* 使用列表解析挑出列表中所有的偶數
* 使用列表解析所有元素平方
```python
numbers = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
[x for x in numbers if x % 2 == 0]
[x * x for x in numbers]
```
> python中高階函數有 `map` `filter` `lambda`
> 高階函數,指可以把函數作為參數傳入,并利用傳入的函數對數據進行處理的函數
* 使用高階函數
* filter實現找偶數
* map實現元素平方
```python
numbers = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
# filter(參數1,參數2)
# 參數1為函數,參數2為待處理的數據
f = filter(lambda x: x % 2 == 0, numbers)
for ff in f:
print(ff)
# map(參數1,參數2)
# 參數1為函數,參數2為待處理的數據
m = map(lambda x: x * x, numbers)
for mm in m:
print(mm)
```
> 使用高階函數增加函數調用開銷,時空效率不如使用列表解析
## 字典解析 dict comprehension
> 同列表解析處理對象為字典
* 21 字典解析
* 字典 {'a': 1, 'b': 2, 'c': 3}
* 字典解析 實現 值平方
```python
d = {'a': 1, 'b': 2, 'c': 3}
{k:v*v for k, v in d.items()}
```
## 迭代器
> 迭代(遍歷),一個一個讀取操作對象叫迭代(遍歷)
> 可迭代(Iterable)對象,能用for...in...迭代的對象
> 迭代器(Iterator),能用next函數不斷獲取它的下一個值,直到迭代器返回`StopIteration`異常,所以可迭代對象都可以通過`iter`函數獲取他的迭代器
* 可迭代&迭代器
* 列表letter 元素 a b c
* 使用for in 遍歷,說明letter是可迭代對象
* 使用iter函數作用于letter,結果就是迭代器
* 然后使用next函數作用迭代器
* 22 迭代器
```python
# 可迭代
# letter就是可迭代對象
letters = ['a', 'b', 'c']
for letter in letters:
print(letter)
# 迭代器
letters = ['a', 'b', 'c']
# it就是迭代器
it = iter(letters)
next(it)
next(it)
next(it)
next(it)
```
> 可迭代對象其實是實現了`__iter__`和`__next__`兩個魔術方法,`iter`與`next`函數實際上調用的就是這兩個魔術方法
* 以上例子背后實現是這樣的
```python
letters = ['a', 'b', 'c']
# 使用iter(序列)將序列(可迭代對象)變成迭代器
it = letters.__iter__()
it.__next__()
it.__next__()
it.__next__()
it.__next__()
```
> 能被`for`循環的都是`可迭代對象`
> 能被`next()`函數獲取下一個值的就是`迭代器`
## 生成器
> 生成器首先是迭代器
> 迭代器和生成器都只能被迭代一次
> 每次迭代的元素不像列表元素已經存在內存中
> 而是每次迭代生成一個元素
* 23 創建生成器并迭代
* 創建1-4生成器 元素平方
* 迭代
* 再次迭代
* 創建1-4生成器
* 使用next()不斷訪問他的下一個元素
```python
g = (x**x for x in range(1, 4))
for x in g:
print(x)
# 再次迭代沒有任何輸出
for x in g:
print(x)
g = (x for x in range(1, 4))
next(g)
next(g)
next(g)
next(g)
```
> 生成器元素動態生成,當迭代對象元素多時,使用生成器節約內存
> 生成器是一個迭代器所以可以使用`next()`函數
## 裝飾器
> 為函數添加額外功能不影響函數主體功能
> 裝飾器實現的基礎 函數可以作為參數傳遞給另一個函數,也可以作為另一個函數的返回值
* 裝飾器結構
```
包裹裝飾器函數(被修飾的函數):
decorator(非關鍵詞收集,關鍵詞收集):
裝飾器內容
return 被修飾函數(非關鍵詞收集,關鍵詞收集)
return decorator
```
* 24 裝飾器記錄函數調用日志
* 函數 add()求兩個數的和
* log()函數里面包裹裝飾器記錄函數調用時間
```python
from datetime import datetime
# 定義裝飾器日志函數
def log(func):
def decorator(*args, **kwargs):
print('Function ' + func.__name__ + ' has been called at ' + datetime.now().strftime('%Y-%m-%d %H:%M:%S'))
return func(*args, **kwargs)
return decorator
# 使用裝飾器
@log
def add(x, y):
return x + y
add(1, 2)
```
> `@`是python提供的語法糖
> 語法糖計算機語言中添加的某種語法
> 這種語法對語言功能沒有影響,更方便程序員使用
> `*arg`和`**kwargs`都是收集參數
> `*arg`非關鍵詞收集,是一個元祖
> `**kwargs`非關鍵詞收集,是一個字典
> 一起用表示收集函數的所有參數
* 以上效果等價于
```python
def add(x, y):
return x + y
add = log(add)
add(1, 2)
```
* 這個時候查看使用裝飾器后的函數名
```python
add.__name__
```
> 用log裝飾完后,add已經不是原來的函數名了
* 使用函數工具`wraps()`
```python
from datetime import datetime
from functools import wraps
def log(func):
# 添加報錯
@wraps(func)
def decorator(*args,**kwargs):
print('function '+func.__name__+" has been called "+datetime.now().strftime('%Y-%m-%d %H:%M:%S'))
return func(*args,**kwargs)
return decorator
@log
def add(x,y):
return x+y
add(6,9)
add.__name__
```