1. python新手常見問題八 標准庫模塊命名
與Python標准庫模塊命名沖突
Python的一個優秀的地方在於它提供了豐富的庫模塊。但是這樣的結果是,如果你不下意識的避免,很容易你會遇到你自己的模塊的名字與某個隨Python附帶的標准庫的名字沖突的情況(比如,你的代碼中可能有一個叫做email.py的模塊,它就會與標准庫中同名的模塊沖突)。
這會導致一些很粗糙的問題,例如當你想載入某個庫,這個庫需要載入Python標准庫里的某個模塊,結果呢,因為你有一個與標准庫里的模塊同名的模塊,這個包錯誤的將你的模塊載入了進去,而不是載入Python標准庫里的那個模塊。這樣一來就會有麻煩了。
相關推薦:《Python視頻教程》
所以在給模塊起名字的時候要小心了,得避免與Python標准庫中的模塊重名。相比起你提交一個「Python改進建議(Python Enhancement Proposal (PEP))」去向上要求改一個標准庫里包的名字,並得到批准來說,你把自己的那個模塊重新改個名字要簡單得多。
相關推薦:
Python新手常見問題七:循環載入模塊
2. python中的問題
上周旁聽了一個大學學長組織的線上Python交流會,里邊不乏充斥著各位行業大牛,講的內容確實精彩,可能對於Python經驗5年+的人來說,是受益匪淺,歡迎程度極高,恨不得跳出屏幕來表示贊同,畢竟很多提到的問題,我在工作中也很常見。
但是作為資歷一般的程序員,有一些理解起來還是有些困難,評論區里同時也還有另外一種聲音:聽不懂啊,還可以再細講一些嗎?
剛畢業,剛開始學Python,可以說說入門的嗎?
走了走了,零基礎滿臉懵……太難了,放棄Python了。我很能理解「另一種聲音」,我當初也是自學Python,剛開始的時候,我連循環結構和分支結構都搞不明白誰是誰,去找有經驗的人問,結果問了幾回人家就煩了,
後來自己從傻瓜式的資料庫軟體維格表入手,一步一步學習數據分析和處理。
再基於維格表學習Python,就容易很多。
所以,學習這種事,還是得靠自己。
根據我自己的經驗來說,想從零開始學Python,以後也確實想找相關的工作,基本是下邊這三種方式:
一、繼續上學。
報個這方面的專業,學上兩三年,老師就在身邊,有啥不懂的問題,直接辦公室走一趟,畢業的時候去找工作不成大問題;
二、看書自學。這塊可以看看GitHub【Python百天之路】,對細節把握很到位!
三、在網上找視頻課自學。
你可以利用碎片時間去學,時間上會更節省,我為了苦學Python大概買了十多門課吧。讀研讀博這件事時間成本比較高,我對自己沒有完全的自信,所以我思考再三,還是決定踏入社會浪潮了。(但是對於學習能力強,本科也比較優秀的學生,非常建議繼續讀研讀博,未來踏入社會起薪會非常高,我現在身邊就有兩個博士大神,我只能膜拜了。。。)
進入社會之後,我基本就是買書和看視頻自學,這回給你們來個全方位安利:
一、網站推薦
1、維格表
可視化資料庫、初學者的法寶,如果你想學習Python,最好還是先學會用這個軟體。在這里,你不僅可以學到什麼是可視化資料庫,還能掌握基本的數據分析和處理知識:篩選、排序、分組,不得不感嘆,功能太強大!
三、課程推薦
其實,除了學習網站和書籍,我還在網易雲課堂、51、慕課、CSDN學院買了不下10套關於Python入門的課,在得到也買了時間管理課。
我自己的話,因為我是想進行系統學習,也想節省一些學習時間,加上我也比較懶,非得有人督促著才能堅持不懈,所以我選了CSDN的Python訓練營。
3. 關於python的問題
你的程序大部分都沒錯,只是對列表my_list中的字元串元素"5"轉數值元素時,要把轉換結果賦值給原元素,
否則列表my_list沒改變,導致處理字元串元素"5"時,出現不支持字元串和整數相除操作的錯誤.
完整的Python程序如下(改動的地方見注釋,僅一處有問題)
my_list = [1, 2, 3, 4, "5"]
my_list[4]=int(my_list[4]) #這里把int(my_list[4])改成my_list[4]=int(my_list[4])
number = int(input("請輸入一個number:"))
for i in my_list:
print(f"{i}/{number}={i/number}")
源代碼(注意源代碼的縮進)
4. Python中一些小問題
__init__方法在類的一個對象被建立時,馬上運行。這個方法可以用來對你的對象做一些你希望的 初始化 。注意,這個名稱的開始和結尾都是雙下劃線。使用__init__方法例11.3 使用__init__方法#!/usr/bin/python
# Filename: class_init.py
class Person:
def __init__(self, name):
self.name = name
def sayHi(self):
print 'Hello, my name is', self.name
p = Person('Swaroop')
p.sayHi()
# This short example can also be written as Person('Swaroop').sayHi()(源文件:code/class_init.py)輸出$ python class_init.py
Hello, my name is Swaroop它如何工作這里,我們把__init__方法定義為取一個參數name(以及普通的參數self)。在這個__init__里,我們只是創建一個新的域,也稱為name。注意它們是兩個不同的變數,盡管它們有相同的名字。點號使我們能夠區分它們。最重要的是,我們沒有專門調用__init__方法,只是在創建一個類的新實例的時候,把參數包括在圓括弧內跟在類名後面,從而傳遞給__init__方法。這是這種方法的重要之處。現在,我們能夠在我們的方法中使用self.name域。這在sayHi方法中得到了驗證。給C++/Java/C#程序員的注釋
__init__方法類似於C++、C#和Java中的 constructor 。
__del__
類似於析構函數
#!/usr/local/bin/python
class Study:
def __init__(self,name=None):
self.name = name
def __del__(self):
print "Iamaway,baby!"
def say(self):
print self.name
study = Study("zhuzhengjun")
study.say()
5. Python編程面試常見問題有哪些
Python編程面試題目一:python下多線程的限制以及多進程中傳遞參數的方式,以及區別
(1)python下多線程的限制以及多進程中傳遞參數的方式
python多線程有個全局解釋器鎖(global interpreter lock),這個鎖的意思是任一時間只能有一個線程使用解釋器,跟單cpu跑多個程序一個意思,大家都是輪著用的,這叫“並發”,不是“並行”。
多進程間共享數據,可以使用 multiprocessing.Value 和 multiprocessing.Array
(2)python多線程與多進程的區別
在UNIX平台上,當某個進程終結之後,該進程需要被其父進程調用wait,否則進程成為僵屍進程(Zombie)。所以,有必要對每個Process對象調用join()方法 (實際上等同於wait)。對於多線程來說,由於只有一個進程,所以不存在此必要性。
多進程應該避免共享資源。在多線程中,我們可以比較容易地共享資源,比如使用全局變數或者傳遞參數。在多進程情況下,由於每個進程有自己獨立的內存空間,以上方法並不合適。此時我們可以通過共享內存和Manager的方法來共享資源。但這樣做提高了程序的復雜度,並因為同步的需要而降低了程序的效率。
Python編程面試題目二:lambada函數
lambda 函數是一個可以接收任意多個參數(包括可選參數)並且返回單個表達式值的函數。 lambda 函數不能包含命令,它們所包含的表達式不能超過一個。不要試圖向lambda 函數中塞入太多的東西;如果你需要更復雜的東西,應該定義一個普通函數,然後想讓它多長就多長。
更多關於Python編程的技巧,干貨,資訊等內容,小編會持續更新。
6. 關於python的問題
這里有兩個知識點:
1、切片,比如有一個字元串:name = 'abcdef',那麼在內存中存儲如圖
取e 是 name[4]或者name[-2]
取ef 是 name[:-2]或者name[:4]
取bc 是name[1:3]或者name[-5:-3] ,需要注意的是,「:」後面取的閉包,也就是不包括本身,這個例子里name[3]的 d是不包括的。
那麼path[:-4]就好理解了,就是取字元串開頭到 -4位置的字元串'c: est.',不包括'h'。
2、轉移字元
python系統中,如果在字元串中使用了一些特殊字元,比如換行、換行、tab製表符等等,還有一些特殊意義的字元,像「 號,『號,需要在字元前面加上「」。即轉義符,通俗的說,就是「」後面的那個字元,不是字元原本的意思了,它代表了另一個字元。
比如常用到的 是代表換行, 是製表符。
但是有時候我們的字元串中,號就是它本身的意思,不作為轉義符,比如題目路徑中的中的號。這個時候就要在字元串前面加上一個'r',告訴系統,字元串裡面的 號,不是轉義符。
所以,你的題目答案就是 c: est.htm
當然,如果題目沒有「r」,也就是 path='c: est.html' 那麼答案就變成了 c: est.htm , 做為了一個製表符處理。
7. 新手關於python的一些基本問題
1,不是,但有py2exe等這樣的庫可以轉換;
2 ,sdk是Software Development Kit 是軟體開發工具包,你的意思應該是JVM這樣的虛擬機,python運行需要虛擬機(PVM),但不像JVM那樣是一個獨立的程序。你要是編寫python程序還是需要到官網下載python來安裝就像JDK一樣,然後如果要開發其他方面的東西可能還需要安裝其他的庫;
3 python作為腳本語言,一個記事本或者本身帶的IDLE就可以差不多了,其他的也有好多的IDE,eclipse上安裝PyDev 插件,sublime text、還有很多其他的一些免費的IDE可以網上搜搜。
8. 菜鳥學python遇到的幾個小問題
A1: Open 函數中 'w' 代表以寫入模式打開文件;( w -- write )
A2: target 代表已經打開的文件實例; target. 後面即 對該打開文件的操作方法;
如: target.truncate([size]) #把文件裁成規定的大小,默認的是裁到當前文件操作標記的位置。如果size比文件的大小還要大,依據系統的不同可能是不改變文件,也可能是用0把文件補到相應的大小,也可能是以一些隨機的內容加上去。
target.write(str) #把str寫到文件中,write()並不會在str後加上一個換行符
9. python的簡單問題
要把代碼發現來才知道,以下是常見的錯誤下面終於要講到當你用到更多的Python的功能(數據類型,函數,模塊,類等等)時可能碰到的問題了。由於篇幅有限,這里盡量精簡,尤其是對一些高級的概念。要想了解更多的細節,敬請閱讀Learning Python, 2nd Edition的逗小貼士地以及逗Gotchas地章節。 打開文件的調用不使用模塊搜索路徑當你在Python中調用open()來訪問一個外部的文件時,Python不會使用模塊搜索路徑來定位這個目標文件。它會使用你提供的絕對路徑,或者假定這個文件是在當前工作目錄中。模塊搜索路徑僅僅為模塊載入服務的。不同的類型對應的方法也不同列表的方法是不能用在字元串上的,反之亦然。通常情況下,方法的調用是和數據類型有關的,但是內部函數通常在很多類型上都可以使用。舉個例子來說,列表的reverse方法僅僅對列表有用,但是len函數對任何具有長度的對象都適用不能直接改變不可變數據類型記住你沒法直接的改變一個不可變的對象(例如,元組,字元串): T = (1, 2, 3) T[2] = 4 # 錯誤 用切片,聯接等構建一個新的對象,並根據需求將原來變數的值賦給它。因為Python會自動回收沒有用的內存,因此這沒有看起來那麼浪費: T = T[:2] + (4,) # 沒問題了: T 變成了 (1, 2, 4) 使用簡單的for循環而不是while或者range 當你要從左到右遍歷一個有序的對象的所有元素時,用簡單的for循環(例如,for x in seq:)相比於基於while-或者range-的計數循環而言會更容易寫,通常運行起來也更快。除非你一定需要,盡量避免在一個for循環里使用range:讓Python來替你解決標號的問題。在下面的例子中三個循環結構都沒有問題,但是第一個通常來說更好;在Python里,簡單至上。 S = "lumberjack" for c in S: print c # 最簡單 for i in range(len(S)): print S[i] # 太多了 i = 0 # 太多了 while i len(S): print S[i]; i += 1 不要試圖從那些會改變對象的函數得到結果諸如像方法list.append()和list.sort()一類的直接改變操作會改變一個對象,但不會將它們改變的對象返回出來(它們會返回None);正確的做法是直接調用它們而不要將結果賦值。經常會看見初學者會寫諸如此類的代碼: mylist = mylist.append(X) 目的是要得到append的結果,但是事實上這樣做會將None賦值給mylist,而不是改變後的列表。更加特別的一個例子是想通過用排序後的鍵值來遍歷一個字典里的各個元素,請看下面的例子: D = {...} for k in D.keys().sort(): print D[k] 差一點兒就成功了——keys方法會創建一個keys的列表,然後用sort方法來將這個列表排序——但是因為sort方法會返回None,這個循環會失敗,因為它實際上是要遍歷None(這可不是一個序列)。要改正這段代碼,將方法的調用分離出來,放在不同的語句中,如下: Ks = D.keys() Ks.sort() for k in Ks: print D[k] 只有在數字類型中才存在類型轉換在Python中,一個諸如123+3.145的表達式是可以工作的——它會自動將整數型轉換為浮點型,然後用浮點運算。但是下面的代碼就會出錯了: S = "42" I = 1 X = S + I # 類型錯誤 這同樣也是有意而為的,因為這是不明確的:究竟是將字元串轉換為數字(進行相加)呢,還是將數字轉換為字元串(進行聯接)呢看在Python中,我們認為逗明確比含糊好地(即,EIBTI(Explicit is better than implicit)),因此你得手動轉換類型: X = int(S) + I # 做加法: 43 X = S + str(I) # 字元串聯接: "421" 循環的數據結構會導致循環盡管這在實際情況中很少見,但是如果一個對象的集合包含了到它自己的引用,這被稱為循環對象(cyclic object)。如果在一個對象中發現一個循環,Python會輸出一個[…],以避免在無限循環中卡住: >>> L = ['grail'] # 在 L中又引用L自身會 >>> L.append(L) # 在對象中創造一個循環 >>> L ['grail', [...]] 除了知道這三個點在對象中表示循環以外,這個例子也是很值得借鑒的。因為你可能無意間在你的代碼中出現這樣的循環的結構而導致你的代碼出錯。如果有必要的話,維護一個列表或者字典來表示已經訪問過的對象,然後通過檢查它來確認你是否碰到了循環。賦值語句不會創建對象的副本,僅僅創建引用這是Python的一個核心理念,有時候當行為不對時會帶來錯誤。在下面的例子中,一個列表對象被賦給了名為L的變數,然後L又在列表M中被引用。內部改變L的話,同時也會改變M所引用的對象,因為它們倆都指向同一個對象。 >>> L = [1, 2, 3] # 共用的列表對象 >>> M = ['X', L, 'Y'] # 嵌入一個到L的引用 >>> M ['X', [1, 2, 3], 'Y'] >>> L[1] = 0 # 也改變了M >>> M ['X', [1, 0, 3], 'Y'] 通常情況下只有在稍大一點的程序里這就顯得很重要了,而且這些共用的引用通常確實是你需要的。如果不是的話,你可以明確的給他們創建一個副本來避免共用的引用;對於列表來說,你可以通過使用一個空列表的切片來創建一個頂層的副本: >>> L = [1, 2, 3] >>> M = ['X', L[:], 'Y'] # 嵌入一個L的副本 >>> L[1] = 0 # 僅僅改變了L,但是不影響M >>> L [1, 0, 3] >>> M ['X', [1, 2, 3], 'Y'] 切片的范圍起始從默認的0到被切片的序列的最大長度。如果兩者都省略掉了,那麼切片會抽取該序列中的所有元素,並創造一個頂層的副本(一個新的,不被公用的對象)。對於字典來說,使用字典的dict.()方法。靜態識別本地域的變數名 Python默認將一個函數中賦值的變數名視作是本地域的,它們存在於該函數的作用域中並且僅僅在函數運行的時候才存在。從技術上講,Python是在編譯def代碼時,去靜態的識別本地變數,而不是在運行時碰到賦值的時候才識別到的。如果不理解這點的話,會引起人們的誤解。比如,看看下面的例子,當你在一個引用之後給一個變數賦值會怎麼樣: >>> X = 99 >>> def func(): ... print X # 這個時候還不存在 ... X = 88 # 在整個def中將X視作本地變數 ... >>> func( ) # 出錯了! 你會得到一個逗未定義變數名地的錯誤,但是其原因是很微妙的。當編譯這則代碼時,Python碰到給X賦值的語句時認為在這個函數中的任何地方X會被視作一個本地變數名。但是之後當真正運行這個函數時,執行print語句的時候,賦值語句還沒有發生,這樣Python便會報告一個逗未定義變數名地的錯誤。事實上,之前的這個例子想要做的事情是很模糊的:你是想要先輸出那個全局的X,然後創建一個本地的X呢,還是說這是個程序的錯誤看如果你真的是想要輸出這個全局的X,你需要將它在一個全局語句中聲明它,或者通過包絡模塊的名字來引用它。默認參數和可變對象在執行def語句時,默認參數的值只被解析並保存一次,而不是每次在調用函數的時候。這通常是你想要的那樣,但是因為默認值需要在每次調用時都保持同樣對象,你在試圖改變可變的默認值(mutable defaults)的時候可要小心了。例如,下面的函數中使用一個空的列表作為默認值,然後在之後每一次函數調用的時候改變它的值: >>> def saver(x=[]): # 保存一個列表對象 ... x.append(1) # 並每次調用的時候 ... print x # 改變它的值 ... >>> saver([2]) # 未使用默認值 [2, 1] >>> saver() # 使用默認值 [1] >>> saver() # 每次調用都會增加! [1, 1] >>> saver() [1, 1, 1] 有的人將這個視作Python的一個特點——因為可變的默認參數在每次函數調用時保持了它們的狀態,它們能提供像C語言中靜態本地函數變數的類似的一些功能。但是,當你第一次碰到它時會覺得這很奇怪,並且在Python中有更加簡單的辦法來在不同的調用之間保存狀態(比如說類)。要擺脫這樣的行為,在函數開始的地方用切片或者方法來創建默認參數的副本,或者將默認值的表達式移到函數裡面;只要每次函數調用時這些值在函數里,就會每次都得到一個新的對象: >>> def saver(x=None): ... if x is None: x = [] # 沒有傳入參數看 ... x.append(1) # 改變新的列表 ... print x ... >>> saver([2]) # 沒有使用默認值 [2, 1] >>> saver() # 這次不會變了 [1] >>> saver() [1] 其他常見的編程陷阱下面列舉了其他的一些在這里沒法詳述的陷阱:在頂層文件中語句的順序是有講究的:因為運行或者載入一個文件會從上到下運行它的語句,所以請確保將你未嵌套的函數調用或者類的調用放在函數或者類的定義之後。 reload不影響用from載入的名字:reload最好和import語句一起使用。如果你使用from語句,記得在reload之後重新運行一遍from,否則你仍然使用之前老的名字。在多重繼承中混合的順序是有講究的:這是因為對superclass的搜索是從左到右的,在類定義的頭部,在多重superclass中如果出現重復的名字,則以最左邊的類名為准。在try語句中空的except子句可能會比你預想的捕捉到更多的錯誤。在try語句中空的except子句表示捕捉所有的錯誤,即便是真正的程序錯誤,和sys.exit()調用,也會被捕捉到。
10. python新手常見的報錯有哪些
1.NameError變數名錯誤
報錯:
>>> print a
Traceback (most recent call last):
File "<stdin>", line 1, in <mole>
NameError: name 'a' is not defined
解決方案:
先要給a賦值。才能使用它。在實際編寫代碼過程中,報NameError錯誤時,查看該變數是否賦值,或者是否有大小寫不一致錯誤,或者說不小心將變數名寫錯了。
註:在Python中,無需顯示變數聲明語句,變數在第一次被賦值時自動聲明。
>>> a=1
>>> print a
1
2.IndentationError代碼縮進錯誤
代碼:
a=1
b=2
if a<b:
print a
報錯:
IndentationError: expected an indented block
原因:
縮進有誤,python的縮進非常嚴格,行首多個空格,少個空格都會報錯。這是新手常犯的一個錯誤,由於不熟悉python編碼規則。像def,class,if,for,while等代碼塊都需要縮進。
縮進為四個空格寬度,需要說明一點,不同的文本編輯器中製表符(tab鍵)代表的空格寬度不一,如果代碼需要跨平台或跨編輯器讀寫,建議不要使用製表符。
解決方案:
a=1
b=2
if a<b:
print a
3.AttributeError對象屬性錯誤
報錯:
>>> import sys
>>> sys.Path
Traceback (most recent call last):
File "<stdin>", line 1, in <mole>
AttributeError: 'mole' object has no attribute 'Path'
原因:
sys模塊沒有Path屬性。
解決方案:
python對大小寫敏感,Path和path代表不同的變數。將Path改為path即可。
>>> sys.path
['', '/usr/lib/python2.6/site-packages']
python知識拓展:
使用dir函數查看某個模塊的屬性
>>> dir(sys)
['__displayhook__', '__doc__', '__egginsert', '__excepthook__', '__name__', '__package__', '__plen', '__stderr__', '__stdin__', '__stdout__', '_clear_type_cache', '_current_frames', '_getframe', 'api_version', 'argv', 'builtin_mole_names', 'byteorder', 'call_tracing', 'callstats', 'right', 'displayhook', 'dont_write_bytecode', 'exc_clear', 'exc_info', 'exc_type', 'excepthook', 'exec_prefix', 'executable', 'exit', 'flags', 'float_info', 'getcheckinterval', 'getdefaultencoding', 'getdlopenflags', 'getfilesystemencoding', 'getprofile', 'getrecursionlimit', 'getrefcount', 'getsizeof', 'gettrace', 'hexversion', 'maxint', 'maxsize', 'maxunicode', 'meta_path', 'moles', 'path', 'path_hooks', 'path_importer_cache', 'platform', 'prefix', 'ps1', 'ps2', 'py3kwarning', 'setcheckinterval', 'setdlopenflags', 'setprofile', 'setrecursionlimit', 'settrace', 'stderr', 'stdin', 'stdout', 'subversion', 'version', 'version_info', 'warnoptions']
4.TypeError類型錯誤
4.1入參類型錯誤
代碼:
t=('a','b','c')
for i in range(t):
print a[i]
報錯:
TypeError: range() integer end argument expected, got tuple.
原因:
range()函數期望的入參是整型(integer),但卻給的入參為元組(tuple)
解決方案:
將入參元組t改為元組個數整型len(t)
將range(t)改為range(len(t))