函數式程式設計
上學期有上一門叫'人工智慧' 的課,老師強行要我們學了一個叫做prolog 的語言,哇那感覺確實難受,思維方式完全和之前學過的不一樣,寫個漢諾塔想了半天,最後還是在網上找了段代碼修改一下(怕被老師發現抄襲)才寫出來,貼一段出來感受一下:
hanoi(N) :- dohanoi(N, 'a', 'b', 'c'). dohanoi(0, _ , _ , _ ) :- !. dohanoi(N, A, B, C) :- N1 is N-1, dohanoi(N1, A, C, B), writeln([move, N, A-->C]), dohanoi(N1, B, A, C).
當時是差不多弄懂了,主要是資料實在太少,debug 都無從談起,一遇上bug 就gg,我現在自己看也有點頭暈。不過據說 prolog 當年能和 Lisp 一爭高下,最近對 Lisp 也有點興趣,等弄完這些就去參拜一下這類函數式語言。
何謂函數式程式設計?廖大這裡寫道:
函數式程式設計就是一種抽象程度很高的程式設計範式,純粹的函數式程式語言所寫的函數沒有變量,因此,任意一個函數,只要輸入是確定的,輸出就是確定的,這種純函數我們稱之為沒有副作用。而允許使用變數的程式設計語言,由於函數內部的變數狀態不確定,同樣的輸入,可能得到不同的輸出,因此,這種函數是有副作用的。
可能看完還是有些不太理解,不急,先看完這幾個小節吧。
高階函數
在數學和電腦科學中,高階函數是至少滿足下列一個條件的函數:
接受一個或多個函數作為輸入
-
輸出一個函數
是說,把函數本身當成參數傳遞,或是回傳一個函數。
>>> min(1, 2) 1 >>> f = min >>> f(1, 2) 1 >>> f <built-in> >>> min <built-in></built-in></built-in>也可以給函數賦值(代碼接上):
>>> min = 10 >>> min(1, 2) Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: 'int' object is not callable >>> f(1, 2) 1 >>> min = f >>> min(1, 2) 1</module></stdin>還可以傳參,例如,一個計算所有數字的和的函數:
>>> def add(a, b): ... return a+b ... >>> def mysum(f, *l): ... a = 0 ... for i in l: ... a = f(a, i) ... return a ... >>> mysum(add, 1, 2, 3) 6 >>> mysum(add, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10) 55當然,將這個f 換成乘法就是計算所有數字的乘積了。 再來看看 python 內建的一些高階函數,常常會用到。 map/reduce記得上學期上雲端運算的課程時依稀有聽過這個詞,不過這課很水,就沒怎麼聽,在這裡看到好像發現不太一樣? ? 不過沒啥說的,簡單說一下每個函數的作用。 對於 map,其計算式可以看成這樣:
map(f, [x1, x2, ..., xn]) = [f(x1), f(x2), ..., f(xn)]對於 reduce,其計算式可以看成這樣:
reduce(f, [x1, x2, x3, x4]) = f(f(f(x1, x2), x3), x4)廖大那裡說得很清楚啦。 filterfilter 和 map 函數類似,接受一個函數和 iterable,傳回也是一個 list,不過其功能是根據函數傳回值是否為 True 來判斷是否保留該值。例如:
def is_odd(n):
return n % 2 == 1
list(filter(is_odd, [1, 2, 4, 5, 6, 9, 10, 15]))
# 结果: [1, 5, 9, 15]
sortedsorted 函數同樣是一個高階函數,對參數key 傳遞函數可以將需要排列的序列經過key 函數處理後再進行排序,不過不會改變序列的值,例如:>>> sorted([36, 5, -12, 9, -21], key=abs)
[5, 9, -12, -21, 36]
裝飾器(decorator)匿名函數就不說了,以後用時再仔細看吧,裝飾器我記得之前看flask 的時候都研究了好久,這次再來複習一下。 簡單裝飾器首先是一個簡單的裝飾器,在每次調用函數前打印出日誌:import logging
def log(func):
def wrapper(*args, **kw):
logging.warn("%s is running" % func.__name__)
func(*args, **kw)
return wrapper
這就是一個極其簡單的裝飾器,如何使用它呢?我最先看到的用法是在需要裝飾的函數前面加上@,但其實這是Python 的一個語法糖,最原始的用法反而更能讓人理解,先定義一個函數f:
def f(): print("in function f") f = log(f)這樣定義了之後,我們再呼叫f 函數:
>>> f() WARNING:root:f is running in function f使用@log 的結果與其一樣,其實@符號作為裝飾器的語法糖,與前面的賦值語句具有相同的功能,使代碼看起來更簡潔明了,避免再一次賦值操作,就像下面這樣:
@log def f(): print("in function f")含參數的裝飾器有時候我們還需要向裝飾器中傳入參數,例如,狀態,層次等信息,只需要在wrapper 函數外再'包裹'一層函數,如下所示:
import logging
def log(level):
def decorator(func):
def wrapper(*args, **kw):
logging.warn("%s is running at level %d" % (func.__name__, level))
return func(*args, **kw)
return wrapper
return decorator
@log(2)
def f():
print("in function f")
>>> f()
WARNING:root:f is running at level 2
in function f
進一步理解為了再進一步理解裝飾器,我們可以打印出函數f 的name 屬性:#对于不加装饰器的 f,其 name 不变
>>> def f():
... print("in function f")
...
>>> f.__name__
'f'
#对于添加装饰器的函数,其 name 改变了
>>> @log
... def f():
... print("in function f")
...
>>> f.__name__
'wrapper'
聯繫到最前面的裝飾器賦值語句,就可以大致明白髮生了什麼:f = log(f)
使得f 指向修改為log(f) 的回傳值,即wrapper 函數。每次執行原函數 f 時,則會呼叫 wrapper 函數,在我們這個範例中,則是先列印日誌,然後執行原函數 f。不過這樣有一個問題,這樣使得原函數f 的元資訊被替換了,關於f 的許多資訊消失不見,這是很難令人接受的,不過好在我們有functools 模組,修改函數為:
import functools import logging def log(func): functools.wraps(func) def wrapper(*args, **kw): logging.warn("%s is running" % func.__name__) func(*args, **kw) return wrapper >>> @log ... def f(): ... print("in function f") ... >>> f.__name__ 'f'另外,還可以對同一個函數添加多個裝飾器:
@a @b @c def f (): # 等价于 f = a(b(c(f)))總結關於函數式編程我也不是很了解,這裡只是大概了解了一下其概念吧,平時肯定還是使用命令式編程用得多。不過有語言是純函數式語言,例如 Haskell 或 Lisp,學習它們會讓人打開一種新思路。 更多[python] 初探'函數式程式設計'相關文章請關注PHP中文網!

要在有限的時間內最大化學習Python的效率,可以使用Python的datetime、time和schedule模塊。 1.datetime模塊用於記錄和規劃學習時間。 2.time模塊幫助設置學習和休息時間。 3.schedule模塊自動化安排每週學習任務。

Python在遊戲和GUI開發中表現出色。 1)遊戲開發使用Pygame,提供繪圖、音頻等功能,適合創建2D遊戲。 2)GUI開發可選擇Tkinter或PyQt,Tkinter簡單易用,PyQt功能豐富,適合專業開發。

Python适合数据科学、Web开发和自动化任务,而C 适用于系统编程、游戏开发和嵌入式系统。Python以简洁和强大的生态系统著称,C 则以高性能和底层控制能力闻名。

2小時內可以學會Python的基本編程概念和技能。 1.學習變量和數據類型,2.掌握控制流(條件語句和循環),3.理解函數的定義和使用,4.通過簡單示例和代碼片段快速上手Python編程。

Python在web開發、數據科學、機器學習、自動化和腳本編寫等領域有廣泛應用。 1)在web開發中,Django和Flask框架簡化了開發過程。 2)數據科學和機器學習領域,NumPy、Pandas、Scikit-learn和TensorFlow庫提供了強大支持。 3)自動化和腳本編寫方面,Python適用於自動化測試和系統管理等任務。

兩小時內可以學到Python的基礎知識。 1.學習變量和數據類型,2.掌握控制結構如if語句和循環,3.了解函數的定義和使用。這些將幫助你開始編寫簡單的Python程序。

如何在10小時內教計算機小白編程基礎?如果你只有10個小時來教計算機小白一些編程知識,你會選擇教些什麼�...

使用FiddlerEverywhere進行中間人讀取時如何避免被檢測到當你使用FiddlerEverywhere...


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

Dreamweaver Mac版
視覺化網頁開發工具

Safe Exam Browser
Safe Exam Browser是一個安全的瀏覽器環境,安全地進行線上考試。該軟體將任何電腦變成一個安全的工作站。它控制對任何實用工具的訪問,並防止學生使用未經授權的資源。

WebStorm Mac版
好用的JavaScript開發工具

mPDF
mPDF是一個PHP庫,可以從UTF-8編碼的HTML產生PDF檔案。原作者Ian Back編寫mPDF以從他的網站上「即時」輸出PDF文件,並處理不同的語言。與原始腳本如HTML2FPDF相比,它的速度較慢,並且在使用Unicode字體時產生的檔案較大,但支援CSS樣式等,並進行了大量增強。支援幾乎所有語言,包括RTL(阿拉伯語和希伯來語)和CJK(中日韓)。支援嵌套的區塊級元素(如P、DIV),

DVWA
Damn Vulnerable Web App (DVWA) 是一個PHP/MySQL的Web應用程序,非常容易受到攻擊。它的主要目標是成為安全專業人員在合法環境中測試自己的技能和工具的輔助工具,幫助Web開發人員更好地理解保護網路應用程式的過程,並幫助教師/學生在課堂環境中教授/學習Web應用程式安全性。 DVWA的目標是透過簡單直接的介面練習一些最常見的Web漏洞,難度各不相同。請注意,該軟體中