Python 學習筆記(五)


1.檢查文件是否存在

我們經常需要從文件中讀取數據或向其中寫入數據,但要做到這一點,我們需要檢查文件是否存在。

import os 
exists = os.path.isfile('/path/to/file')

2.讀取CSV文件

import csv
csv_mapping_list = []
with open("/path/to/data.csv") as my_data:
    csv_reader = csv.reader(my_data, delimiter=",")
    line_count = 0
    for line in csv_reader:
        if line_count == 0:
            header = line
        else:
            row_dict = {key: value for key, value in zip(header, line)}
            csv_mapping_list.append(row_dict)
        line_count += 1

3.SQLAlchemy

SQLAlchemy是Python編程語言下的一款ORM框架,該框架建立在數據庫API之上,使用關系對象映射進行數據庫操作,簡言之便是:將對象轉換成SQL,然后使用數據API執行SQL並獲取執行結果。

關於ORM:

全稱Object Relational Mapping(對象關系映射)。

特點是操縱Python對象而不是SQL查詢,也就是在代碼層面考慮的是對象,而不是SQL,體現的是一種程序化思維,這樣使得Python程序更加簡潔易讀。

具體的實現方式是將數據庫表轉換為Python類,其中數據列作為屬性,數據庫操作作為方法。優點是(1)簡潔易讀:將數據表抽象為對象(數據模型),更直觀易讀;(2)可移植:封裝了多種數據庫引擎,面對多個數據庫,操作基本一致,代碼易維護;(3)更安全:有效避免SQL注入。

 4.Flask-RESTful 參數解析

Flask-RESTful 內置了支持驗證請求數據,它使用了一個argparse 的庫。

from flask.ext.restful import reqparse

##定義解析器 parser
= reqparse.RequestParser()
##添加規則,如果是必填項,還可以添加 required =true定義是否必填,通過location=['form','args'...]定義作用域 parser.add_argument(
'rate', type=int, help='Rate to charge for this resource')
##參數 args
= parser.parse_args()
##獲取指定的參數
key-name-values = args.get('XXX')

help--定義了報錯時的提示信息。

 5.數據格式化

Flask-RESTful 提供了 fields 模塊和 marshal_with() 裝飾器。類似 Django ORM 和 WTForm,可以使用 fields 模塊來響應中格式化結構。

flask.ext.restful.marshal_with(fieldsenvelope=None)

A decorator that apply marshalling to the return values of your methods.

主要是解決以下報錯:

TypeError:Object of type XXXX is not JSON serialzable.

 導入模塊的方式;

from flask.ext.restful import fields, marshal_with

 案例

from collections import OrderedDict
from flask.ext.restful import fields, marshal_with

###一定是字典結構 resource_fields
= { 'task': fields.String, 'uri': fields.Url('todo_ep') } class TodoDao(object): def __init__(self, todo_id, task): self.todo_id = todo_id self.task = task # This field will not be sent in the response self.status = 'active' class Todo(Resource): @marshal_with(resource_fields) def get(self, **kwargs): return TodoDao(todo_id='my_todo', task='Remember the milk')

此外,fields.Nested(),fields.List()也是常用從方法。

 6.Python實現多任務

進程>線程>協程

主進程:執行的時候,默認的進程稱作主進程;子進程,在主進程中可以開啟子進程。

multiprocessing模塊提供了類似threading模塊的接口,並對進程的各種操作進行了良好的封裝,提供了各種進程間通信的接口例如Pipe, Queue等等,可以實現進程間的通信,同步等操作。

import time
from multiprocessing import Process

# 創建子進程
p = Process(target=run, args=("Ail",)) # target進程執行的任務/函數, args傳參數,可選,可迭代(元組)
#啟動進程
p.start()

 7.進程ID

import os
os.getpid() ##當前進程ID
os.getppid() ##獲取當前進程的父進程的id

 8.全局變量在多個進程中不能共享

在子進程中修改全局變量對父進程中的全局變量沒有影響。因為父進程在創建子進程時對全局變量做了一個備份,父進程中的全局變量與子進程的全局變量完全是不同的兩個變量。全局變量在多個進程中不能共享。

即:如果是全局變量,則每個進程都會擁有一份全局變量,各自操作各自的全局變量。

9.進程join方法

有時候會需要父進程等待子進程結束再執行父進程后面的代碼,此時可以考慮使用join()方法。

例子如下:

import time
from multiprocessing import Process
import os

def run():
    print("子進程開啟")
    time.sleep(2)
    print("子進程結束")

if __name__ == "__main__":
    print("父進程啟動")
    p = Process(target=run)
    p.start()
    p.join()  # 等待子進程結束后,再往下執行
    print("父進程結束")

# 輸出結果
父進程啟動
子進程開啟
子進程結束
父進程結束

 jion()也可以理解為阻塞主進程,此處后面的代碼,主進程暫不執行。它可以設置timeout。

 10.多進程process的常用方法

(1) start():啟動子進程實例(創建子進程);

(2) is_alive():判斷子進程是否還在活着;如果任務完成,則false;

(3) join([timeout]):是否等待子進程執行結束,或等待多少秒;

(4) terminate():不管任務是否完成,立即終止子進程;

(5) close() :關閉 Process 對象,釋放與之關聯的所有資源。如果底層進程仍在運行,則會引發 ValueError 。注意,如果資源釋放后(已調用colse()),再執行 is_alive()會報錯。

11.進程池 

 如果要啟動大量的子進程,可以用進程池的方式批量創建子進程。

from multiprocessing.pool import Pool

# 創建多個進程,表示可以同時執行的進程數量。默認大小是CPU的核心數 p = Pool(8)

# 創建進程,放入進程池統一管理 p.apply_async(funcation-name, funcation-args=(???,)) ###非阻塞式;還可以添加回調函數。此外還有一種阻塞式:p.apply()--注意:(1)阻塞式,進程池中一個任務
完成之后,才能開始下一個任務;(2)
這個沒有回調函數參數。 
# 如果我們用的是進程池,在調用join()之前必須要先close(),並且在close()之后不能再繼續往進程池添加新的進程(即停止添加任務) p.close() # 進程池對象調用join,會等待進程吃中所有的子進程結束完畢再去結束父進程 p.join()

12.進程間通信

需要使用到了multiprocessing模塊的Queue(隊列)。

from multiprocessing import Process, Queue
q = Queue() ##創建隊列
q.put('??') ##將 obj 放入隊列;還有兩個參數[, block[, timeout]。如果可選參數 block 是True(默認值)而且timeout是None默認值), 將會阻塞當前進程,直到有空的緩沖槽。
q.full()  ##判斷隊列是否已滿;如果隊列是滿的,返回True,反之返回False 。
q.qsize() ##返回隊列的大致長度。由於多線程或者多進程的上下文,這個數字是不可靠的。
q.get()  ##從隊列中取出並返回對象。注意:先進先出。可選參數[block[, timeout]];如果可選參數 block 是True(默認值) 而且timeout是None(默認值), 將會阻塞當前進程,直到隊列中出現可用的對象。
q.colse() ##指示當前進程將不會再往隊列中放入對象。一旦所有緩沖區中的數據被寫入管道之后,后台的線程會退出。這個方法在隊列被gc回收時會自動調用。

 

參考

1.快速入門 — Flask-SQLAlchemy 2.0 documentation

http://www.pythondoc.com/flask-sqlalchemy/quickstart.html

2.Python3多進程multiprocessing模塊的使用

https://www.jianshu.com/p/a5f10c152c20

3.multiprocessing --- 基於進程的並行

https://docs.python.org/zh-cn/3.7/library/multiprocessing.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM