首頁 > 軟體

Python命令列引數化的四種方式詳解

2022-06-27 10:00:28

大家好,在日常編寫 Python 指令碼的過程中,我們經常需要結合命令列引數傳入一些變數引數,使專案使用更加的靈活方便

本篇文章我將羅列出構建 Python 命令列引數的 4 種常見方式

它們分別是:

  • 內建 sys.argv 模組
  • 內建 argparse 模組
  • 內建 getopt 模組
  • 第三方依賴庫 click

1. sys.argv

構建命令列引數最簡單、常見的方式是利用內建的「 sys.argv 」模組

它是將引數以一個有序的列表傳入,所以在使用時傳參順序必須固定

因此,這種方式適用於引數個數少且場景固定的專案中

import sys

if __name__ == '__main__':
    # 獲取參數列
    # 注意:sys.argv[0] 代表第一個引數,即:指令碼名稱「1_sys.argv.py」
    # 其他參數列
    args = sys.argv[1:]

    # 引數個數
    args_length = len(sys.argv) if sys.argv else 0

    print("排除執行主檔案引數,其他參數列為:", args)

    print("引數總數:", args_length)

# 使用
# python3 1_sys.argv.py arg1 arg2
# 排除執行主檔案引數,其他參數列為: [arg1, arg1]
# 引數總數:3

需要注意的是,在指令碼中通過「 sys.argv 」獲取的參數列中,第一個引數代表指令碼主檔名稱

2. argparse

內建的 argparse 模組可以非常輕鬆地編寫出友好的命令列引數指令碼,並且它能自動生成幫助使用手冊,在使用者給程式傳入無效引數時能丟擲清晰的錯誤資訊

官方檔案

使用它構建命令列引數包含 3 個步驟:

構建引數解析物件新增引數新增引數解析引數

1.構建命令列引數解析物件

import argparse
...
# 構建一個命令列引數解析物件
parser = argparse.ArgumentParser(description='命令列引數')
...

2.新增命令列引數

需要指出的是,--arg1 用於指定引數名稱,-a1 代表 dest 目標變數值(簡寫)

...
# 設定3個引數
# 引數1:arg1,整型,非必須傳入引數
# 引數2:arg2,字串,非必須傳入引數,包含預設值「xag」
# 引數3:arg3,字串型別,必須傳入的引數
parser.add_argument('--arg1', '-a1', type=int, help='引數1,非必須引數')
parser.add_argument('--arg2', '-a2', type=str, help='引數2,非必須引數,包含預設值', default='xag')
parser.add_argument('--arg3', '-a3', type=str, help='引數3,必須引數', required=True)
...

3.解析出引數值

...
# 解析引數,獲取所有的命令列引數(Namespace),然後轉為字典
args = vars(parser.parse_args())

# 獲取所有引數
print("所有命令列引數為:")
for key in args:
    print(f"命令列引數名:{key},引數值:{args[key]}")
...

使用的時候,我們就可以通過「 -h / --help 」命令引數檢視幫助檔案

# 檢視命令列引數幫助檔案
python3 2_argparse.py --help
# 或
python3 2_argparse.py -h

上面新增的 3 個引數,引數 arg1、arg2 非必須傳值,arg3 必須傳值,另外引數 arg2 指定了預設值

# 引數arg3必須,引數arg1和引數arg2非必須,其中引數arg2設定了預設值

# 傳入引數arg3
# python3 2_argparse.py --arg3 123
# python3 2_argparse.py -a3 123 
xingag@xingagdeMacBook-Pro args % python3 2_argparse.py -a3 123  
所有命令列引數為:
命令列引數名:arg1,引數值:None
命令列引數名:arg2,引數值:xag
命令列引數名:arg3,引數值:123

# 傳入引數arg1、arg3
xingag@xingagdeMacBook-Pro args % python3 2_argparse.py -a1 111  -a3 123  
所有命令列引數為:
命令列引數名:arg1,引數值:111
命令列引數名:arg2,引數值:xag
命令列引數名:arg3,引數值:123

# 傳入引數arg1、arg2、arg3
xingag@xingagdeMacBook-Pro args % python3 2_argparse.py -a1 111 -a2 222  -a3 123
所有命令列引數為:
命令列引數名:arg1,引數值:111
命令列引數名:arg2,引數值:222
命令列引數名:arg3,引數值:123

3. getopt

getopt 是 Python 中一個內建標準模組,可以結合 sys.argv 模組,直接解析指令碼執行時引數

使用格式:getopt(args,shortopts,longopts = [])

其中

args

參數列,可以通過 sys.argv 獲取,可以參考上面

shortopts 短引陣列成的字串

定義短引數,如果引數有值,需要在短引數後追加一個「 : 」符號

傳參使用方式:-n 23

longopts 長參數列

定義長參數列時,如果某個引數有值,需要在短引數後追加一個「 = 」符號

傳參使用方式:–port 8080

這裡以傳入資料庫連線引數為例(引數包含 ip、使用者名稱、密碼、資料庫名稱)進行講解

from getopt import getopt
import sys

# 獲取引數
# sys.argv[1:]:獲取除指令碼檔名外的所有命令列引數
# opts:存有所有選項及其輸入值的元組列表
# args:去除有用的輸入以後剩餘的部分
opts, args = getopt(sys.argv[1:], 'i:u:p:d:', ['ip=', 'user=', 'pwd=', 'db='])

# 獲取引數值
# 短引數
# python3 4_getopt.py -i 127.0.0.1 -u root -p 123456 -d mysqldb
# 長引數
# python3 4_getopt.py --ip 127.0.0.1 -u root -p 123456 -d mysqldb
ip_pre = [item[1] for item in opts if item[0] in ('-i', '--ip')]
ip = ip_pre[0] if len(ip_pre) > 0 else None
print("引數ip:", ip)

user_pre = [item[1] for item in opts if item[0] in ('-u', '--user')]
user = user_pre[0] if len(user_pre) > 0 else None
print("引數user:", user)

pwd_pre = [item[1] for item in opts if item[0] in ('-p', '--pwd')]
pwd = pwd_pre[0] if len(pwd_pre) > 0 else None
print("引數pwd:", pwd)

db_pre = [item[1] for item in opts if item[0] in ('-d', '--db')]
db = db_pre[0] if len(db_pre) > 0 else None
print("引數db:", db)

在執行指令碼時,我們可以利用「 短引數 」或「 長引數 」形式進行傳遞

# 測試
# 短引數
python3 4_getopt.py -i 127.0.0.1 -u root -p 123456 -d mysqldb

# 長引數
python3 4_getopt.py --ip 127.0.0.1 --user root --pwd 123456 --db mysqldb

4. click

click 作為第三方依賴庫,它為命令列工具封裝了大量的方法,可以非常方便實現命令列引數

專案地址

首先,我們需要安裝依賴庫 click

import click

# 安裝依賴
# pip3 install -U click

@click.command()
@click.option('--arg1', default='111', help='引數arg1,預設值為「111」')
@click.option('--arg2', type=int, help='引數arg2')
@click.option('--arg3', type=str, help='引數arg3')
def start(arg1, arg2, arg3):
    """
    基於引數arg1、引數arg2、引數arg3執行專案
    :param arg1:
    :param arg2:
    :param arg3:
    :return:
    """
    print("引數arg1值為:", arg1)
    print("引數arg2值為:", arg2)
    print("引數arg3值為:", arg3)


if __name__ == '__main__':
    start()

然後,在主執行函數上通過裝飾器設定引數即可

比如,上面就定義了 3 個命令列引數 arg1、arg2、arg3,並設定了引數的型別及預設值

最後,在執行指令碼時只需要按引數設定傳遞對應的值即可

# 不包含引數
xingag@xingagdeMacBook-Pro args % python3 3_click.py 
引數arg1值為: 111
引數arg2值為: None
引數arg3值為: None

# 包含引數arg1
xingag@xingagdeMacBook-Pro args % python3 3_click.py --arg1 test1
引數arg1值為: test1
引數arg2值為: None
引數arg3值為: None

# 包含引數arg1、arg2
# 注意:arg2的引數型別為整形,傳入的引數必須能轉為整形,否則會報錯
xingag@xingagdeMacBook-Pro args % python3 3_click.py --arg1 test1 --arg2 222  
引數arg1值為: test1
引數arg2值為: 222
引數arg3值為: None

# 包含引數arg1、arg2、arg3
xingag@xingagdeMacBook-Pro args % python3 3_click.py --arg1 test1 --arg2 222 --arg3 test3
引數arg1值為: test1
引數arg2值為: 222
引數arg3值為: test3

最後

上面通過範例講解了實現 Python 命令列引數常見的 4 種方式

對於一些簡單自用且不那麼正規的場景,個人覺得可以考慮用 sys.argv 模組快速構建命令列引數;而對一些引數多、面向使用者的正式生產環境,建議利用 argparse 模組或 click 依賴來建立命令列引數

到此這篇關於Python命令列引數化的四種方式詳解的文章就介紹到這了,更多相關Python命令列引數化內容請搜尋it145.com以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援it145.com!


IT145.com E-mail:sddin#qq.com