Python 編寫ORM時的重難點掌握

前言:

       最近才狠下心來 準備做一個自己的博客 原先FuckBlog項目由於後端小夥伴加班而擱置,因此 作爲團隊PM的我自己也要開始做技術方面了,準備自己先寫一個博客看看。

      備註- ORM全稱:object related mapping  對象關係映射

0x00 爲什麼需要寫一個ORM

首先,我覺得數據庫操作不封裝是很傻比的。原來我寫了一個數據庫導入工具,全篇導出都是sql語句 什麼增刪改查都他媽齊活的在各個py裏面跑來跑去。給大家上一張圖:

大家體會到這種亂跑的辛酸了麼 從那次失敗的架構我就說:再不用orm我他媽就是一傻逼

其次就是不安全,我這裏再給大家舉一個反例 使我們FuckBlog項目裏面 後端小夥伴採用了一個異常簡單的後臺模板 我在查看代碼的時候 發現了問題 我們看用戶驗證的代碼:

看到了麼 傳輸的用戶名密碼 居然是直接放進sql語句拼接的。大家知道怎麼構造 password來達到我們想要的任意用戶名都可以登錄的效果了麼 有幾個月了 我簡單說一下思路 首先引號閉合 閉合之後 然後在+ or +構造萬能查詢語句  只要能查詢成功,就到讓session進行賦值。

最後呢 就是在web中 因爲:

一處異步調用 處處異步調用  

我們在查詢數據庫中肯定不能因爲數據量過大而放棄其他的請求 這樣效率非常慢所以這方面的控制 以及上文所述的問題 需要我們去封裝 而方便我們的調用和請求。因此我們需要自己寫一個orm工具類 去完成異步的增刪改查

 

0x01 ORM 編寫的一些難點

 

我跟着廖雪峯大神的博客 來學習 期間也看了不少人的跑通代碼 自己的疑問點期初看的時候也很多當然 自己慢慢一點一點啃 啃幾天就會發現豁然開朗。

代碼加上測試一共三百多行,非常簡潔,當然我估計註釋就能佔到八九十行,包括別人的也包括自己第一篇學習的困惑和不瞭解。也算是比較實用吧。 我先貼我第一版學習跑通的代碼 然後呢 我會慢慢在後面進行闡述。

 

NO1: 爲何要使用asyncore 和 aiomysql 這兩個庫

假設我們調用數據庫的請求不知一個,比如用戶小王訪問我們網站,獲取你以前的文章,那麼東北社會你關哥也在同一時間訪問我們網站,而文章比較多,小王的請求需要5秒才能返回結果。採用同步的話,那社會你關哥 就要等着小王請求王城才能進行請求(獲得服務器關注)麼? 顯然不行,因此需要採用異步的收發請求 。而Python 中實現這個的就是asyncore 他封裝了HTTP UDP SSL 的異步協議 可以讓單線程 也可以異步收發請求。(如果你想自己實現套字節的異步收發返回,可以小小參考一下我的這篇網絡腳本編寫

那aiohttp是什麼鬼 aiomysql 又是什麼叼東西。他們都是基於asyncore 實現的異步http庫 異步mysql 庫 調用他們就可以實現異步請求在http 和 mysql 上。記住:一處異步 處處異步

 

NO2:關於日誌的記錄

引用日誌模塊logging 沒有什麼好說的 需要注意的是 在我們編寫服務端的時候 良好的日誌記錄習慣很重要 不要被pycharm慣壞了 動不動print大法 debug大法 另外我想補充的是:logging這個吊玩兒,在多線程記錄的時候會出錯,需要改寫其中的某些方法,別問我是如何知道的。對了,

level=logging.INFO

這個INFO大寫。

 

NO3:*args **kw是什麼東西?

*args 和 **kwargs 主要用於函數定義。 **kw就是**kwargs的縮寫,可以傳遞數量不一的變量,他們的核心是前面的星號 一顆星和兩顆星 而不是後面的args 你寫成*fuckyou 都沒事。只不過是約定俗稱而已。那麼這個屌絲東西怎麼用呢?我們看一段示例代碼:(我改自gitbook Python進階

輸出結果:

我們再來看**kwargs

**kwargs :該參數允許你將不定長度的鍵值對, 作爲參數傳遞給一個函數。 如果你想要在一個函數裏處理帶名字的參數, 你應該使用**kwargs

你肯定回想 啥叫鍵值對 帶名字的參數又是什麼鬼 我們來看這個例子:

 

怎麼樣現在傳的時候是不是有點小明白 就像傳遞一個字典一樣,比如這樣:

主要傳進去my_info 是一個字典就好了。

一般來講傳遞的順序是 var *args **kwargs

這裏面就順便提一下,字典的get方法用法是get(key,value) 如果沒有key對應的鍵值 則返回設定value

比如

返回就是:

email ==> [email protected]
[email protected]
Fuck None
name ==> sly
sly
Fuck None

 

NO3: yield 和 yield from 語法

 

我們都知道yield 或者說對yield 比較熟悉 因爲我們教學的案例常常就是 yield result 當一個 生成器(英文:generator)。但是我們爲了弄清楚這一系列的東西 我們需要首先弄清楚迭代器 生成器這些鬼東西。在這方面 除了官方文檔 我還查閱了 這個 這個還有這個 當然 IBM的也不錯 等等 我就不一一列出了。

生成器的簡析:

我們爲啥需要生成器?假設我們需要處理草榴的所有用戶信息,如果一次性就處理1000萬的用戶信息列表非常耗費內存,我們的本地電腦內存不夠用,那麼就需要一個分批處理草榴用戶信息生成器的東西,當我們調用一次的時候返回1000用戶信息列表即可 ,下一次調用就返回uid在1001-2000的用戶就好了。但是你可能會問:函數裏面的return咋知道你是下一次調用還是第三次第四次調用 給你返回你想要的值呢?而這就是yield 存在的神奇方法,它能夠記住。

而正因爲yield 存在才使得我們不需要擁有存儲 1000萬草榴用戶信息列表,就能逐步得到這些信息。內存佔用極小。

那麼可能會有人問:適用於生成器的對象自身需要可迭代能力麼 也就是說我必須要是一個字典列表啥的才行麼?

事實上生成器調用的對象自身必須擁有可迭代能力,之所以你認爲傳遞列表或者字典是你把迭代在Python裏面的識別狹義化了。

什麼是可迭代?什麼東西可以記住當前調用位置?

可迭代是指一種可以在容器中逐個提取元素的能力。

(容器:將多個元素組合在一起的數據結構,常見的容器有 dict list tuple str 文本流 以及他們這些的變形比如OrderedDict)

迭代器的內部狀態可以記住當前調用位置

Python是如何識別一個對象擁有可迭代能力?

一個可迭代對象必須具備:

  • __iter__()

(爲啥該命名方法前後有__因爲這是Python特殊方法,以示區分,在OOP編程的後續會給大家講到)

迭代器呢則必須具備以下特殊方法:2.x是next()

  • __iter__()
  • __next__()

我們來看廖雪峯在IBM workplace上給的yield 斐波拉切數列案例

你最終會發現這個yield 讓返回的對象變成了 generator 一個生成器。 它讓你關注的點更多的在算法實現上,而非存儲上面。

那麼我們該如何自己去實現這個迭代器呢?

調用和擁有yield 的函數一樣,同上。

如果還有疑問或者我的描述有錯誤的可以在博客評論中提出(mail寫好我回復你會收到郵件~)

解釋了yield 我們來看一下 yield from 

關於yield from 這個Python 3.3 才支持的東西我們看一下:

首先,yield from 是爲了解決什麼問題而出現的。

看到上文我們發現一個問題,yield 不能脫離代碼單獨出來用,在一個生成器中調用另外一個生成器想要用,咋辦 那麼我們就需要yield from

yield from的的歷史可以參考 這個PEP

總之大意是原本的yield語句只能將CPU控制權還給直接調用者,當你想要將一個generator或者coroutine裏帶有yield語句的邏輯重構到另一個generator(原文是subgenerator)裏的時候,會非常麻煩,因爲外面的generator要負責爲裏面的generator做消息傳遞;所以某人有個想法是讓python把消息傳遞封裝起來,使其對程序猿透明,於是就有了yield from

 

對於簡單的迭代器,yield from iterable本質上等於for item in iterable: yield item的縮寫版 yield from允許子生成器直接從調用者接收其發送的信息或者拋出調用時遇到的異常,並且返回給委派生產器一個值

 

那麼在本次學習orm的過程中你就把他理解爲異步執行即可 先別管原理了。

如果大家仍舊很感興趣 可以參考這篇文章 我能力有限 就不畫蛇添足了。

 

 

NO4. __pool 和這個__init__ 這些東西是啥?

這個就簡單說一下 前面一條槓 就是非公開變量 兩條槓私有變量 一條槓能調用 兩條槓就不允許外部調用。不像Java 那樣有什麼private 什麼的 別再和我說不能阻止外部調用很不安全 私有變量 不可以 You are Adult.

__str__ __init__ __name__ 這些都是特殊方法(或者魔術方法) 內置的 詳細幹嘛自己去Python官網看。

 

NO5.  @asyncore.coroutine 是什麼鬼?

它能夠將一個生成器generator標記爲coroutine類型,然後扔進Eventloop 異步執行。

這裏我們需要回去複習廖雪峯大神關於asyncore的講解。(這告訴我們 翹課早晚是要還的 不管你是網課還是自學)

相關文章
相關標籤/搜索