Python 是一種動態且強型別的程式語言。它透過型別提示,同時採用了鴨子型別與漸進式型別。命令式、宣告式(例如函式式)與物件導向的程式設計_風格_都受到支援,但在內部,Python 中的所有東西都是物件。
Python 非常重視程式碼的可讀性,並且(類似於 Haskell)使用顯著縮排來表示函式、方法與類別的定義。
Python 由 Guido van Rossum 創造,並於 1991 年首次發布。Python 軟體基金會負責管理並引導 Python 與 CPython 開發所需的資源,並透過Python 增強提案(PEPs)接收社群成員對語言變更的提案。
目前發行版本的完整說明文件可在 docs.python.org 找到。
這個概念會介紹 4 項 Python 的主要語言特色:
def 關鍵字與 return 關鍵字),大體而言,Python 賽道的內容、測試與分析器工具都遵循 PEP 8 與 PEP 257 所描述的 Python 程式碼風格慣例,並額外(強烈)建議不要使用單一字母的變數名稱。
Python 之禪(PEP 20)與什麼是 Pythonic?則闡述了更多哲學。
在 Python 賽道中,變數一律使用snake_case撰寫,常數則使用SCREAMING_SNAKE_CASE
在 Python 中,建立變數或常數並不需要任何關鍵字。程式設計師可以使用指定運算子=,把名稱(也稱為_變數_)綁定到任何型別的物件:<name> = <value>。名稱在其生命週期內可以重新指定(或重新綁定)為不同的值(不同的物件型別)。
例如,my_first_variable可以用=重新指定許多次,而且每次重新指定都可以指向不同的物件型別:
>>> my_first_variable = 1 # my_first_variable bound to an integer object of value one.
>>> my_first_variable = 2 # my_first_variable re-assigned to integer value 2.
>>> print(type(my_first_variable))
<class 'int'>
>>> print(my_first_variable)
2
>>> my_first_variable = "Now, I'm a string." # <--You may re-bind a name to a different object type and value.
>>> print(type(my_first_variable))
<class 'str'>
>>> my_first_variable = 'You can call me "str".' # <--Strings can be declared using single or double quote marks.
>>> print(my_first_variable)
You can call me "str".
>>> import collections
>>> my_first_variable = collections.Counter([1,1,2,3,3,3,4,5,6,7]) # <--Now my_first_variable has been re-bound to a Counter object.
>>> print(type(my_first_variable))
<class 'collections.Counter'>
>>> print(my_first_variable)
Counter({3: 3, 1: 2, 2: 1, 4: 1, 5: 1, 6: 1, 7: 1})
常數是指在程式中只應該指定一次的名稱。它們應該定義在模組(檔案)層級,而且程式中所有函式與類別通常都能看到它們。使用SCREAMING_SNAKE_CASE表示這個名稱不應該被重新指定,其值也不應該被修改。
# All caps signal that this is intended as a constant.
MY_FIRST_CONSTANT = 16
# Re-assignment will be allowed by the compiler & interpreter,
# but this is VERY strongly discouraged.
# Please don't do this, it could create problems in your program!
MY_FIRST_CONSTANT = "Some other value"
在 Python 中,功能單位被封裝在函式裡,而函式本身也是物件(這就像是一路都是烏龜)。
函式可以單獨執行、作為引數傳給其他函式、形成巢狀結構,或綁定到類別上。當函式綁定到類別名稱時,就稱為方法。相關的函式與類別(連同它們的方法)可以一起放在同一個檔案或模組中,並可部分或整體匯入,供其他程式使用。
def關鍵字會開始一個函式定義。每個函式可以在()括號內有零個或多個正式參數,後面接著一個:冒號。函式_主體_的敘述從def的下一行開始,而且必須_縮排成一個區塊_:
# The body of a function is indented by 2 spaces & prints the sum of the numbers.
def add_two_numbers(number_one, number_two):
total = number_one + number_two
print(total)
>>> add_two_numbers(3, 4)
7
# Inconsistent indentation in your code blocks will raise an error.
>>> def add_three_numbers_misformatted(number_one, number_two, number_three):
... result = number_one + number_two + number_three # This was indented by 4 spaces.
... print(result) # <--This was only indented by 3 spaces.
...
...
File "<stdin>", line 3
print(result)
^
IndentationError: unindent does not match any outer indentation level
函式會透過return關鍵字_明確地_回傳一個值或物件:
# Function definition on first line, explicit return used on final line.
def add_two_numbers(number_one, number_two):
return number_one + number_two
# Calling the function in the Python shell returns the sum of the numbers.
>>> add_two_numbers(3, 4)
7
# Assigning the function call to a variable and printing
# the variable will also return the value.
>>> sum_with_return = add_two_numbers(5, 6)
>>> print(sum_with_return)
11
在return後面沒有_明確_運算式的函式,會_隱含地_回傳None物件。None的細節會在後續的概念中介紹。就本練習與本說明而言,None是一個代表空無或 null 的佔位符:
# This function will return `None`
def square_a_number(number):
square = number * number
return # <-- note that this return is not followed by an expression
# Calling the function in the Python shell appears
# to not return anything at all.
>>> square_a_number(2)
>>>
# Using print() with the function call shows that
# the function is actually returning the **None** object.
>>> print(square_a_number(2))
None
省略return的函式也會_隱含地_回傳None物件。這表示如果函式中沒有使用return,Python 會替你回傳None物件。
# This function omits a return keyword altogether
def add_two_numbers(number_one, number_two):
result = number_one + number_two
>>> add_two_numbers(5, 7)
>>> print(add_two_numbers(5, 7))
None
# Assigning the function call to a variable and printing
# the variable will also show None.
>>> sum_without_return = add_two_numbers(5, 6)
>>> print(sum_without_return)
None
函式是透過在其名稱後面加上()來呼叫或叫用的。呼叫定義在類別或模組內的函式時,會使用點(.)標記法。
>>> def raise_to_power(number, power):
... return number ** power
...
>>> raise_to_power(3,3) # Invoking the function with the arguments 3 and 3.
27
# A mis-match between the number of parameters and the number of arguments will raise an error.
>>> raise_to_power(4,)
...
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: raise_to_power() missing 1 required positional argument: 'power'
# Calling methods or functions in classes and modules.
>>> start_text = "my silly sentence for examples."
>>> str.upper(start_text) # <--Calling the upper() method from the built-in str class on start_text.
'MY SILLY SENTENCE FOR EXAMPLES.'
# Because a string is an instance of the str class, methods can also be called on them "directly".
>>> start_text = "my silly sentence for examples."
>>> start_text.upper() # <--Calling the upper() method on start_text directly.
'MY SILLY SENTENCE FOR EXAMPLES.'
# Alternatively, we can skip the variable assignment (although this gets messy quick).
>>> "my silly sentence for examples.".upper()
'MY SILLY SENTENCE FOR EXAMPLES.'
# Importing the math module
>>> import math
>>> math.pow(2,4) # <--Calling the pow() function from the math module.
16.0
Python 中的註解以不屬於字串一部分的#開頭,並在行尾結束。與許多其他程式語言不同,Python 不支援多行註解的標記。註解區塊的每一行都必須以#字元開頭。
註解會被翻譯員忽略:
# This is a single line comment.
x = "foo" # This is an in-line comment.
# This is a multi-line
# comment block over multiple lines --
# these should be used sparingly.
函式主體的第一個敘述可以選擇性地放一個文件字串,用來簡潔地總結函式或物件的用途。文件字串使用三個雙引號(""")宣告,並縮排到與程式區塊相同的層級:
# An example from PEP257 of a multi-line docstring
# reformatted to use Google style non-type hinted docstrings.
# Some additional details can be found in the Sphinx documentation:
# https://www.sphinx-doc.org/en/master/usage/extensions/napoleon.html#getting-started
def complex(real=0.0, imag=0.0):
"""Form a complex number.
Keyword Arguments:
real (float): The real part of the number (default 0.0)
imag (float): The imaginary part of the number (default 0.0)
"""
if imag == 0.0 and real == 0.0:
return complex_zero
文件字串會被自動化文件工具讀取,也可以在函式、方法或類別名稱上呼叫特殊屬性.__doc__來取得。任何規模、只要需要說明文件的程式都建議使用它們,其慣例規範於 PEP257 中。
文件字串也可以當作輕量化的單元測試,可由 PyTest 讀取與執行,或匯入doctest模組後執行。測試與doctest會在後續的概念中介紹。
# An example on a user-defined function using a Google style docstring.
>>> def raise_to_power(number, power):
"""Raise a number to an arbitrary power.
Parameters:
number (int): The base number.
power (int): The power to raise the base number to.
Returns:
int: The number raised to the specified power.
Takes a number and raises it to the specified power, returning the result.
"""
return number ** power
...
# Calling the .__doc__ attribute of the function and printing the result.
>>> print(raise_to_power.__doc__)
Raise a number to an arbitrary power.
Parameters:
number (int): The base number.
power (int): The power to raise the base number to.
Returns:
int: The number raised to the specified power.
Takes a number and raises it to the specified power, returning the result.
...
# Printing the __doc__ attribute of the built-in type: str.
>>> print(str.__doc__)
str(object='') -> str
str(bytes_or_buffer[, encoding[, errors]]) -> str
Create a new string object from the given object. If encoding or
errors is specified, then the object must expose a data buffer
that will be decoded using the given encoding and error handler.
Otherwise, returns the result of object.__str__() (if defined)
or repr(object).
encoding defaults to 'utf-8'.
errors defaults to 'strict'.