sys.argv 是 Python 存取命令列參數的核心機制,以列表形式儲存所有傳遞給腳本的參數。掌握其結構、索引規則、解析模式與實戰技巧,是開發 CLI 工具、自動化腳本、可配置程式的必備技能。
import sys
print(sys.argv)
# 執行:python script.py arg1 arg2 arg3
# 輸出:['script.py', 'arg1', 'arg2', 'arg3']
| 索引 | 含義 | 說明 |
|---|---|---|
| sys.argv[0] | 腳本路徑/名稱 | 可能是相對路徑、絕對路徑、或僅檔名,視呼叫方式而定 |
| sys.argv[1:] | 實際傳遞參數 | 使用者輸入的所有參數,索引從 1 開始 |
| len(sys.argv) | 總參數數 | 包含腳本名稱,實際參數數 = len(sys.argv) - 1 |
#!/usr/bin/python
import sys
import os
# 範例 1:直接執行命令列參數指定的程式
# 執行:python sample1.py notepad
os.system(sys.argv[1])
#!/usr/bin/python
import sys
def readfile(filename):
"""讀取並輸出檔案內容"""
with open(filename, 'r') as f:
for line in f:
print(line, end='') # 避免雙重換行
if __name__ == '__main__':
# 檢查參數數量
if len(sys.argv) < 2:
print('No action specified.')
sys.exit(1)
# 解析第一個參數判斷模式
first_arg = sys.argv[1]
if first_arg.startswith('--'):
# 選項模式:--version, --help
option = first_arg[2:] # 移除 '--'
if option == 'version':
print('Version 1.2')
elif option == 'help':
print("""This program prints files to the standard output.
Any number of files can be specified.
Options include:
--version : Prints the version number
--help : Display this help""")
else:
print('Unknown option.')
sys.exit(1)
else:
# 檔案模式:所有參數視為檔案名稱
for filename in sys.argv[1:]:
try:
readfile(filename)
except IOError as e:
print(f"Error reading {filename}: {e}", file=sys.stderr)
sys.exit(1)
$ python sample.py --version
Version 1.2
$ python sample.py --help
This program prints files...
$ python sample.py a.txt b.txt
內容 of a.txt
內容 of b.txt
| 模式 | 適用場景 | 優點 | 缺點 |
|---|---|---|---|
| 手動解析 sys.argv | 簡單腳本、少量參數、無相依需求 | 零相依、完全控制、啟動快 | 易出錯、維護難、缺乏標準功能 |
| argparse 模組(標準庫) | 標準 CLI 工具、複雜參數、需自動生成說明 | 功能完整、標準化、自動 --help、型別轉換、驗證 | 啟動稍慢、程式碼較多 |
| click / typer(第三方) | 現代 CLI、裝飾器風格、型別提示整合 | 語法優雅、自動完成、型別安全、文檔生成 | 需安裝套件、學習曲線 |
import argparse
parser = argparse.ArgumentParser(description='處理檔案的示範程式')
parser.add_argument('files', nargs='*', help='要處理的檔案列表')
parser.add_argument('-v', '--version', action='version', version='1.2')
parser.add_argument('-n', '--number', type=int, default=10, help='顯示行數')
parser.add_argument('--upper', action='store_true', help='轉大寫輸出')
args = parser.parse_args()
for filename in args.files:
with open(filename) as f:
lines = f.readlines()[:args.number]
for line in lines:
print(line.upper() if args.upper else line, end='')
$ python script.py -n 5 --upper file1.txt file2.txt
$ python script.py --help
usage: script.py [-h] [-v] [-n NUMBER] [--upper] [files ...]
...
import os
script_dir = os.path.dirname(os.path.abspath(sys.argv[0]))
import sys
def main():
if len(sys.argv) > 1:
# 有檔案參數
for f in sys.argv[1:]:
process_file(f)
else:
# 無參數,讀取 stdin(支援管道)
for line in sys.stdin:
process_line(line)
if __name__ == '__main__':
main()
# 手動實作 -- 分隔
args = sys.argv[1:]
if '--' in args:
split_idx = args.index('--')
options = args[:split_idx]
files = args[split_idx+1:]
else:
# 簡單啟發式:以 - 開頭為選項
options = [a for a in args if a.startswith('-')]
files = [a for a in args if not a.startswith('-')]
os.path.abspath 正規化。python script.py "file name.txt"sys.argv = [os.fsdecode(a) for a in sys.argv] 處理。args = sys.argv[1:]print("error", file=sys.stderr)sys.argv 是 Python 命令列參數的原始入口,結構為 [script_path, arg1, arg2, ...]。簡單腳本可手動解析,正式專案強烈建議使用 argparse(標準庫、功能完整、自動生成說明)。掌握索引規則、解析模式、常見技巧與最佳實務,能開發出健壯、易用、符合 Unix 哲學的 CLI 工具。