os.Args
程式獲取執行他時給出的引數,可以通過os包來實現。先看程式碼:
package main
import (
"fmt"
"os"
"strconv"
)
func main () {
for idx, args := range os.Args {
fmt.Println("引數" + strconv.Itoa(idx) + ":", args)
}
}
執行起來得到的如下:
$go run main.go 1 3 -X ?
引數0: /tmp/go-build116558042/command-line-arguments/_obj/exe/main
引數1: 1
引數2: 3
引數3: -X
引數4: ?
可以看到,命令列引數包括了程式路徑本身,以及通常意義上的引數。
程式中os.Args的型別是 []string ,也就是字串切片。所以可以在for迴圈的range中遍歷,還可以用 len(os.Args) 來獲取其數量。
如果不想要輸出os.Args的第一個值,也就是可執行檔案本身的資訊,可以修改上述程式:
for idx, args := range os.Args[1:] {
將range後面的切片,去掉第一個元素。
輸出切片的所有元素,還有更簡潔的方式:
fmt.Println(strings.Join(os.Args[1:], "\n"))
fmt.Println(os.Args[1:])
/*
後一種方式的結果是[1 3 -X ?],這是fmt.Println輸出切片的格式
*/
flag包
flag包相比單純的通過os.Args切片分析命令列引數,提供了更強的能力。
來看個例子:
package main
import (
"fmt"
"flag"
)
var b = flag.Bool("b", false, "bool型別引數")
var s = flag.String("s", "", "string型別引數")
func main() {
flag.Parse()
fmt.Println("-b:", *b)
fmt.Println("-s:", *s)
fmt.Println("其他引數:", flag.Args())
}
$ go run main.go
-b: false
-s:
其他引數: []
------------------------------------
$ go run main.go -b
-b: true
-s:
其他引數: []
------------------------------------
$ go run main.go -b -s test others
-b: true
-s: test
其他引數: [others]
------------------------------------
$ go run main.go -help
Usage of /tmp/go-build080353851/command-line-arguments/_obj/exe/main:
-b bool型別引數
-s string
string型別引數
exit status 2
定義引數
使用flag包,首先定義待解析命令列引數,也就是以”-“開頭的引數,比如這裡的 -b -s -help等。-help不需要特別指定,可以自動處理。
這裡指定了兩個引數,-b和-s:
var b = flag.Bool("b", false, "bool型別引數")
var s = flag.String("s", "", "string型別引數")
-----------------
原型:
func Bool(name string, value bool, usage string) *bool
func String(name string, value string, usage string) *string
通過flag.Bool和flag.String,建立了2個指標b和s,分別指向bool型別和string型別的變數。所以後續要通過 *b 和 *s 使用變數值。
flag.Bool和flag.String的引數有3個,分別是命令列引數名稱,預設值,提示字串。
引數 功能
name 命令列引數名稱,比如 -b, -help
value 預設值,未顯式指定的引數,給出隱式的預設值,比如本例中-b未給出的話,*b=false
usage 提示資訊,如果給出的引數不正確或者需要檢視幫助 -help,那麼會給出這裡指定的字串
解析引數
flag使用前,必須首先解析:
flag.Parse()
使用引數
上文已經說明,通過flag方法定義好的引數變數指標,通過間接引用操作即可使用其內容:
fmt.Println("-b:", *b)
fmt.Println("-s:", *s)
未解析引數
引數中沒有能夠按照預定義的引數解析的部分,通過flag.Args()即可獲取,是一個字串切片。
fmt.Println("其他引數:", flag.Args())
1
需要注意的是,從第一個不能解析的引數開始,後面的所有引數都是無法解析的。即使後面的引數中含有預定義的引數:
$ go run main.go -b stop -s test others
-b: true
-s:
其他引數: [stop -s test others]
上面例子中,解析到stop,就已經無法繼續解析了,即使後面給出了預定義好的-s,也是不能獲取出來的。
本作品採用《CC 協議》,轉載必須註明作者和本文連結