PYTHON

Lesson 7

Lecturer : 乘一

Debugging?

這有甚麼難的

先看這個code

a = 1 + input()
b = a + c
d = b + 24
m = 57*d//0
print(6442-m) 
#出錯,應該說錯誤百出
#你是不是一臉問號這是甚麼毒瘤

ㄟ對我抄上上次簡報

方法1: print大法

Print

a = 1 + input()
print(a)
b = a + c
d = b + 24
m = 57*d//0
print(6442-m) 
#a的結果與預期不符
#恭喜找出來a出錯!

但如果問題不在一開始呢...?

Print的問題

print(第一個) -> 正確
print(第二個) -> 正確
......
print(好多好多個) -> 終於錯了
print(第n個) -> 不符預期(第n個是根據第n-1個)
print(第n-1個) -> 不符預期(第n-1個是根據第n-2個)
......
print(第x個) -> 終於對了

耗費大量資源與輸出極度冗雜

如何解決?

方法2: logging

logging

日誌紀錄工具

  • 避免多餘的輸出

  • 處理彈性極高

  • 紀錄歷程方便DEBUG

logging

日誌紀錄工具

import logging
#就...import模組(還沒忘吧!?
logging.basicConfig(level=logging.DEBUG)
#一開始的基本設定,level表示輸出的最低層級
logger = logging.getLogger( __name__ )
#創建一個紀錄器

各種層級

名稱 功能 對應函式
debug 除錯時使用 .debug()
info 記錄各種資訊時使用 .info()
warning 警告(預設層級) .warning()
error 錯誤(出錯) .error()
critical 嚴重錯誤 .critical()

logging

怎麼使用?

import logging
logging.basicConfig(level=logging.DEBUG)
logger = logging.getLogger( __name__ )
a = 1+4
logger.debug(a)
b = a+6
print(b)
logger.info("print b")
#DEBUG:__main__:5
#11
#INFO:__main__:print b

logging

如果層級變為INFO...?

import logging
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger( __name__ )
a = 1+4
logger.debug(a)
b = a+6
print(b)
logger.info("print b")
#11
#INFO:__main__:print b
#DEBUG那行消失了!

logging

好像還不夠厲害

import logging
logger = logging.getLogger( __name__  )
def some_method():
    logger.info('begin of some_method')
def another_method():
    logger.info('begin of another_mathod')
    
def main():
    logging.basicConfig(level=logging.DEBUG)
    some_method()
    another_method()
    
if __name__ == "__main__":
    main()

logging

把記錄存入檔案

import logging
logging.basicConfig(filename='檔案名稱', filemode='w',level=logging.INFO)
#filemode是寫入方式
#預設是a(ppend),寫入會接在上一個後面
#w(rite)是複寫,也就是說會覆蓋掉之前的紀錄
logger = logging.getLogger( __name__ )
a = 1+4
logger.debug(a)
b = a+6
print(b)
logger.info("print b")

#執行後log會寫入檔案中

不過...這樣還是會輸出一堆東西ㄟ?

方法3: pdb

pdb

python debugger

除錯流程:

  • 設立中斷點

  • 發現錯誤

  • 透過指令解決問題

  • 移除中斷點

各種指令

這些到底是甚麼...

指令 功能
b 行數 在指定行插入中斷點
c 執行程式碼,直到遇到中斷點
l 輸出前後各五行的程式碼
ll 輸出所有程式碼
p 變數名 輸出變數現在的值
s 執行下一行程式碼(進入function)
n 執行下一行程式碼(進入function)
q 離開

pdb

要怎麼用呢...?

pdb

還可以怎麼用呢...?

#寫在程式碼內
import pdb
pdb.set_trace()
#插入中斷點
#python3.7版後可以不用import
#插入中斷點改為直接使用函式:
breakpoint()

可是...我的問題是跳出一堆奇怪的錯誤訊息ㄟ?

方法4: Google大神

說明文件

超級好用(?

  • 內容詳細

  • 官方正版

  • 通常會有範例

  • 備課的時候很常用到

錯誤訊息?

好多好可怕...

list[3] = 1
print(list[3])
#Traceback (most recent call last):
#  File "main.py", line 75, in <module>
#    list[3] = 1
#TypeError: 'type' object does not support item assignment
#他到底在寫甚麼...QAQ

錯誤訊息?

不算解決的解決

  1. 找到最後一行錯誤訊息

  2. 在google複製貼上

  3. 你可能就會找到答案

Stackoverflow

程式設計師的組成要素

  • 程式設計領域的問答網站

  • 可以問問題和回答

  • 基本上你想的到的問題都找的到答案

  • 超級好用!!!

Google 搜尋

這有甚麼好教的???

  • 一堆人不會用Google...(包括我

  • 要點:用英文搜尋!!!

  • 英文爛也沒關係

方法5: ChatGPT

ChatGPT

對啦我就跟風

  • 原本應該是聊天AI

  • 但功能過於變態

  • AI罵我字太多放下頁

ChatGPT

AI好兇...

小社賽~

小社賽~

  • 時間: 12/23-12/25

  • 只能用python!

  • 記得先申請codeforces帳號

  • 並加入建北電資group

下課啦~~~