用python输出12和8的最大公_重点汇总-python常见问题1
1. 簡述函數式編程
解釋一: 在函數式編程中,函數是基本單位,變量只是一個名稱,而不是一個存儲單元。除了匿名函數外,Python還使fliter(),map(),reduce(),apply()函數來支持函數式編程。
解釋二: 廖---函數是Python內建支持的一種封裝,我們通過把大段代碼拆成函數,通過一層一層的函數調用,就可以把復雜任務分解成簡單的任務,這種分解可以稱之為面向過程的程序設計。函數就是面向過程的程序設計的基本單元。
而函數式編程(請注意多了一個“式”字)——Functional Programming,雖然也可以歸結到面向過程的程序設計,但其思想更接近數學計算。
函數式編程就是一種抽象程度很高的編程范式,純粹的函數式編程語言編寫的函數沒有變量,因此,任意一個函數,只要輸入是確定的,輸出就是確定的,這種純函數我們稱之為沒有副作用。而允許使用變量的程序設計語言,由于函數內部的變量狀態不確定,同樣的輸入,可能得到不同的輸出,因此,這種函數是有副作用的。
函數式編程的一個特點就是,允許把函數本身作為參數傳入另一個函數,還允許返回一個函數!
解釋三: 維基百科---函數式編程是一種編程模型,他將計算機運算看做是數學中函數的計算,并且避免了狀態以及變量的概念。
2. 什么是匿名函數,匿名函數有什么局限性
解釋一:匿名函數,也就是lambda函數,通常用在函數體比較簡單的函數上。匿名函數顧名思義就是函數沒有名字,因此不用擔心函數名沖突。不過Python對匿名函數的支持有限,只有一些簡單的情況下可以使用匿名函數。
解釋二: fluent-python---Python 簡單的句法限制了 lambda 函數的定義體只能使用純表達式。 換句話說, lambda 函數的定義體中不能賦值, 也不能使用 while和 try 等 Python 語句,在參數列表中最適合使用匿名函數。除了作為參數傳給高階函數之外, Python 很少使用匿名函數。
3. 如何捕獲異常,常用的異常機制有哪些?
如果我們沒有對異常進行任何預防,那么在程序執行的過程中發生異常,就會中斷程序,調用python默認的異常處理器,并在終端輸出異常信息。
try...except...finally語句:當try語句執行時發生異常,回到try語句層,尋找后面是否有except語句。找到except語句后,會調用這個自定義的異常處理器。except將異常處理完畢后,程序繼續往下執行。finally語句表示,無論異常發生與否,finally中的語句都要執行。
assert語句:判斷assert后面緊跟的語句是True還是False,如果是True則繼續執行print,如果是False則中斷程序,調用默認的異常處理器,同時輸出assert語句逗號后面的提示信息。
with語句:如果with語句或語句塊中發生異常,會調用默認的異常處理器處理,但文件還是會正常關閉
補充:記錄異常 logging 模塊,拋出錯誤 raise語句
4. copy()與deepcopy()的區別
copy是淺拷貝,只拷貝可變對象的父級元素。 deepcopy是深拷貝,遞歸拷貝可變對象的所有元素。
參考文章
5. 函數裝飾器有什么作用(常考)
裝飾器本質上是一個Python函數,它可以讓其他函數在不需要做任何代碼變動的前提下增加額外功能,裝飾器的返回值也是一個函數對象。它經常用于有切面需求的場景,比如:插入日志、性能測試、事務處理、緩存、權限校驗等場景。有了裝飾器,就可以抽離出大量與函數功能本身無關的雷同代碼并繼續重用。
6. 簡述Python的作用域以及Python搜索變量的順序
Python作用域簡單說就是一個變量的命名空間。代碼中變量被賦值的位置,就決定了哪些范圍的對象可以訪問這個變量,這個范圍就是變量的作用域。在Python中,只有模塊(module),類(class)以及函數(def、lambda)才會引入新的作用域。Python的變量名解析機制也稱為 LEGB 法則:本地作用域(Local)→當前作用域被嵌入的本地作用域(Enclosing locals)→全局/模塊作用域(Global)→內置作用域(Built-in)
7. 新式類和舊式類的區別,如何確保使用的類是新式類
為了統一類(class)和類型(type),python在2.2版本引進來新式類。在2.1版本中,類和類型是不同的。
為了確保使用的是新式類,有以下方法:
放在類模塊代碼的最前面 __metaclass__ = type
從內建類object直接或者間接地繼承
在python3版本中,默認所有的類都是新式類。
8. 簡述__new__和__init__的區別
創建一個新實例時調用__new__,初始化一個實例時用__init__,這是它們最本質的區別。
new方法會返回所構造的對象,init則不會.
new函數必須以cls作為第一個參數,而init則以self作為其第一個參數.
9. Python垃圾回收機制(常考)
Python GC主要使用引用計數(reference counting)來跟蹤和回收垃圾。在引用計數的基礎上,通過“標記-清除”(mark and sweep)解決容器對象可能產生的循環引用問題,通過“分代回收”(generation collection)以空間換時間的方法提高垃圾回收效率。
引用計數
PyObject是每個對象必有的內容,其中ob_refcnt就是做為引用計數。當一個對象有新的引用時,它的ob_refcnt就會增加,當引用它的對象被刪除,它的ob_refcnt就會減少.引用計數為0時,該對象生命就結束了。
優點:
簡單 實時性
缺點:
維護引用計數消耗資源 循環引用
標記-清除機制
基本思路是先按需分配,等到沒有空閑內存的時候從寄存器和程序棧上的引用出發,遍歷以對象為節點、以引用為邊構成的圖,把所有可以訪問到的對象打上標記,然后清掃一遍內存空間,把所有沒標記的對象釋放。
分代技術
分代回收的整體思想是:將系統中的所有內存塊根據其存活時間劃分為不同的集合,每個集合就成為一個“代”,垃圾收集頻率隨著“代”的存活時間的增大而減小,存活時間通常利用經過幾次垃圾回收來度量。
Python默認定義了三代對象集合,索引數越大,對象存活時間越長。
10. Python中的 @property 有什么作用?如何實現成員變量的只讀屬性?
@property裝飾器就是負責把一個方法變成屬性調用,通常用在屬性的get方法和set方法,通過設置@property可以實現實例成員變量的直接訪問, 又保留了參數的檢查。另外通過設置get方法而不定義set方法可以實現成員變量的只讀屬性。
11. *args and **kwargs
*args代表位置參數,它會接收任意多個參數并把這些參數作為元組傳遞給函數。**kwargs代表的關鍵字參數,允許你使用沒有事先定義的參數名,另外,位置參數一定要放在關鍵字參數的前面。
12. 有用過with statement嗎?它的好處是什么?具體如何實現?
with語句適用于對資源進行訪問的場合,確保不管使用過程中是否發生異常都會執行必要的“清理”操作,釋放資源,比如文件使用后自動關閉、線程中鎖的自動獲取和釋放等。
13. what will be the output of the code below? explain your answer?
def extend_list(val, list=[]): # 考察默認參數的坑
list.append(val)
return list
list1 = extend_list(10)
list2 = extend_list(123, []) # 不使用默認參數的 [ ]
list3 = extend_list('a')
print(list1)
print(list2)
print(list3)
In [158]: list1
Out[158]: [10, 'a'] # 記住,當函數的參數是可變參數時要極其小心,list即為可變,但
In [159]: list2 # 定義了list,重新生成
Out[159]: [123]
In [160]: list3
Out[160]: [10, 'a']
上述可參考廖的教程:
默認參數很有用,但使用不當,也會掉坑里。默認參數有個最大的坑,演示如下:
def add_end(L=[]):
L.append('END')
return L
>>> add_end([1, 2, 3]) # 正常調用似乎沒問題
[1, 2, 3, 'END']
>>> add_end() # 第一次使用默認參數調用
['END']
>>> add_end() # 開始異常了
['END', 'END']
# 很多初學者很疑惑,默認參數是[],但是函數似乎每次都“記住了”上次添加了'END'后的list。
# Python函數在定義的時候,默認參數L的值就被計算出來了,即[],因為默認參數L也是一個變量,它指向對象[],
每次調用該函數,如果改變了L的內容,則下次調用時,默認參數的內容就變了,不再是函數定義時的[]了。
# 要修改上面的例子,我們可以用None這個不變對象來實現:
def add_end(L=None):
if L is None:
L = []
L.append('END')
return L
定義默認參數要牢記一點:默認參數必須指向不變對象!
class Parent(object): # 考察繼承
x = 1
class Child1(Parent):
pass
class Child2(Parent):
pass
print(Parent.x, Child1.x, Child2.x) # [1,1,1]
Child1.x = 2
print(Parent.x, Child1.x, Child2.x) # [1,2,1]
Partent.x = 3
print(Parent.x, Child1.x, Child2.x) # [3,2,3]
14. 在一個二維數組中,每一行都按照從左到右遞增的順序排序,每一列都按照從上到下遞增的順序排序。請完成一個函數,輸入這樣的一個二維數組和一個整數,判斷數組中是否含有該整數。
arr = [[1,4,7,10,15], [2,5,8,12,19], [3,6,9,16,22], [10,13,14,17,24], [18,21,23,26,30]] # 豎著排列更形象
def getNum(num, data=None): # 他人做法
while data:
if num > data[0][-1]:
del data[0]
print(data)
getNum(num, data=None)
elif num < data[0][-1]:
data = list(zip(*data))
del data[-1]
data = list(zip(*data))
print(data)
getNum(num, data=None)
else:
return True
data.clear()
return False
if __name__ == '__main__':
print(getNum(18, arr))
# ------------------------
In [237]: def find_num(arr, x): # 我的做法
...: L = []
...: for i in arr:
...: for k in i:
...: L.append(k)
...: M = set(L) - set([x])
...: if M == set(L):
...: print('false')
...: else:
...: print('true') # find_num(arr, 10) 測試結果: True
15. 獲取最大公約數、最小公倍數
最大公約數
def gcd(a, b): # 這個就是大名鼎鼎的 歐幾里德 算法,又稱輾轉相除法
while a != 0:
a, b = b % a, a
return b
def maxCommon(a, b): # 這么寫也可以
while b:
a, b = b, a%b
return a # 這個return注意要和while并列,否則會出現問題!
最小公倍數
def minCommon(a, b):
c = a*b
while b:
a, b = b, a%b
return c//a # c 除以最大公約數,即得最小公倍數
16. 獲取中位數
def median(data):
data.sort()
half = len(data) // 2
return (data[half] + data[~half])/2 # ~ 是按位反轉,二進制數0 1對換
按位翻轉
計算機中的符號數有三種表示方法,即原碼、反碼和補碼
17. 輸入一個整數,輸出該數二進制表示中1的個數。其中負數用補碼表示
def getOneCount(num):
if num > 0:
count = b_num.count('1')
print(b_num)
return count
elif num < 0:
b_num = bin(~num)
count = 8 - b_num.count('1')
return count
else:
return 8
if __name__ == '__main__':
print(getOneCount(5))
print(getOneCount(-5))
print(getOneCount(0))
18. B+樹的結構 ----待解決
19. Redis 并發
總結
以上是生活随笔為你收集整理的用python输出12和8的最大公_重点汇总-python常见问题1的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 什么是腰椎间盘脱出
- 下一篇: python socket编程之双方相互