Описание пакета flag языка программирования Go
Categories:
Использование
Определите флаги с помощью flag.String, Bool, Int и т. д.
Это объявляет целочисленный флаг -n
, хранящийся в указателе nFlag
, с типом *int
:
import «flag»
var nFlag = flag.Int("n", 1234, "сообщение справки для флага n")
При желании можно привязать флаг к переменной с помощью функций Var().
var flagvar int
func init() {
flag.IntVar(&flagvar, "flagname", 1234, "сообщение справки для flagname")
}
Или можно создать пользовательские флаги, которые удовлетворяют интерфейсу Value
(с указателями-приемниками), и связать их с разбором флагов с помощью
flag.Var(&flagVal, "name", "сообщение справки для flagname")
Для таких флагов значением по умолчанию является просто начальное значение переменной.
После определения всех флагов вызовите
flag.Parse()
чтобы проанализировать командную строку в определенные флаги.
Затем флаги можно использовать напрямую. Если вы используете сами флаги, все они являются указателями; если вы связываете их с переменными, они являются значениями.
fmt.Println(«ip имеет значение », *ip)
fmt.Println(«flagvar имеет значение », flagvar)
После разбора аргументы, следующие за флагами, доступны как срез flag.Args
или по отдельности как flag.Arg(i)
. Аргументы индексируются от 0
до flag.NArg-1
.
Синтаксис флагов командной строки ¶
Допускаются следующие формы:
-flag
--flag // также допускаются двойные тире
-flag=x
-flag x // только небулевые флаги
Можно использовать один или два тире; они эквивалентны. Последняя форма не допускается для булевых флагов, поскольку значение команды
cmd -x *
где *
— подстановочный знак оболочки Unix, изменится, если есть файл с именем 0, false и т. д. Для отключения булевого флага необходимо использовать форму -flag=false
.
Разбор флагов прекращается непосредственно перед первым аргументом, не являющимся флагом («-» является аргументом, не являющимся флагом), или после терминатора «–».
- Целочисленные флаги принимают значения
1234
,0664
,0x1234
и могут быть отрицательными. - Булевы флаги могут быть:
1, 0, t, f, T, F, true, false, TRUE, FALSE, True, False
Флаги продолжительности принимают любой ввод, допустимый для time.ParseDuration
.
Набор флагов командной строки по умолчанию управляется функциями верхнего уровня. Тип FlagSet
позволяет определять независимые наборы флагов, например для реализации подкоманд в интерфейсе командной строки. Методы FlagSet
аналогичны функциям верхнего уровня для набора флагов командной строки.
Пример
package main
import (
"errors"
"flag"
"fmt"
"os"
"strings"
"time"
)
// Пример 1: Флаг строки с именем "species" и значением по умолчанию "gopher"
var species = flag.String("species", "gopher", "the species we are studying")
// Пример 2: Два флага (длинный и короткий) с общей переменной
var gopherType string
func init() {
const (
defaultGopher = "pocket"
usage = "the variety of gopher"
)
flag.StringVar(&gopherType, "gopher_type", defaultGopher, usage)
flag.StringVar(&gopherType, "g", defaultGopher, usage+" (shorthand)")
}
// Пример 3: Пользовательский тип флага - срез интервалов времени
type interval []time.Duration
// String реализует интерфейс flag.Value
func (i *interval) String() string {
if len(*i) == 0 {
return ""
}
var b strings.Builder
for idx, d := range *i {
if idx > 0 {
b.WriteString(", ")
}
b.WriteString(d.String())
}
return b.String()
}
// Set реализует интерфейс flag.Value
func (i *interval) Set(value string) error {
// Разрешаем множественные установки флага для накопления значений
for _, dt := range strings.Split(value, ",") {
duration, err := time.ParseDuration(strings.TrimSpace(dt))
if err != nil {
return fmt.Errorf("invalid duration %q: %v", dt, err)
}
*i = append(*i, duration)
}
return nil
}
var intervalFlag interval
func init() {
flag.Var(&intervalFlag, "deltaT", "comma-separated list of intervals to use between events")
}
func main() {
// Парсим флаги
flag.Parse()
// Выводим значения флагов
fmt.Println("Species:", *species)
fmt.Println("Gopher type:", gopherType)
fmt.Println("Intervals:", intervalFlag.String())
// Пример использования
if len(intervalFlag) == 0 {
fmt.Println("No intervals specified. Use -deltaT flag")
os.Exit(1)
}
// Демонстрация работы с интервалами
for i, d := range intervalFlag {
fmt.Printf("Event %d will happen after %v\n", i+1, d)
time.Sleep(d) // В реальном коде здесь была бы полезная работа
}
}
Как использовать:
- Сборка:
go build -o app
- Примеры запуска:
# Простой запуск
./app -species=rabbit -gopher_type=arctic -deltaT=1s,2s,3s
# Использование короткого флага
./app -g=arctic -deltaT=500ms,1s
# Просмотр помощи
./app -help
Переменные
var ErrHelp = errors.New("flag: help requested")
ErrHelp
- это ошибка, возвращаемая при вызове флага -help
или -h
, но такой флаг не определен.
var Usage = func() {
fmt.Fprintf(CommandLine.Output(), "Usage of %s:\n", os.Args[0])
PrintDefaults()
}
Usage
печатает сообщение об использовании всех определенных флагов командной строки в выходной файл CommandLine
, который по умолчанию является os.Stderr.
Функция вызывается при возникновении ошибки во время разбора флагов.
Функция - это переменная, которая может быть изменена для указания на пользовательскую функцию. По умолчанию она печатает простой заголовок и вызывает PrintDefaults; подробности о формате вывода и о том, как им управлять, см. в документации к PrintDefaults.
Пользовательские функции могут выбрать выход из программы; по умолчанию выход происходит в любом случае, поскольку стратегия обработки ошибок в командной строке установлена на ExitOnError.