55

I'd like to use getopts inside a function that I have defined in my .bash_profile. The idea is I'd like to pass in some flags to this function to alter its behavior.

Here's the code:

function t() {
    echo $*
    getopts "a:" OPTION
    echo $OPTION
    echo $OPTARG
}

When I invoke it like this:

t -a bc

I get this output:

-a bc
?
 

What's wrong? I'd like to get the value bc without manually shifting and parsing. How do I use getopts correctly inside a function?

EDIT: corrected my code snippet to try $OPTARG, to no avail

EDIT #2: OK turns out the code is fine, my shell was somehow messed up. Opening a new window solved it. The arg value was indeed in $OPTARG.

4

3 回答 3

112

正如@Ansgar 指出的那样,您的选项的参数存储在 中${OPTARG},但这并不是在getopts函数内部使用时唯一需要注意的事情。${OPTIND}您还需要通过取消设置或声明它来确保它是函数本地的local,否则在多次调用该函数时会遇到意外行为。

t.sh

#!/bin/bash

foo()
{
    foo_usage() { echo "foo: [-a <arg>]" 1>&2; exit; }

    local OPTIND o a
    while getopts ":a:" o; do
        case "${o}" in
            a)
                a="${OPTARG}"
                ;;
            *)
                foo_usage
                ;;
        esac
    done
    shift $((OPTIND-1))

    echo "a: [${a}], non-option arguments: $*"
}

foo
foo -a bc bar quux
foo -x

示例运行:

$ ./t.sh
a: [], non-option arguments:
a: [bc], non-option arguments: bar quux
foo: [-a <arg>]

如果你注释掉# local OPTIND,这就是你得到的:

$ ./t.sh
a: [], non-option arguments:
a: [bc], non-option arguments: bar quux
a: [bc], non-option arguments:

除此之外,它的用法与在函数之外使用时相同。

于 2013-05-20T17:54:19.600 回答
17

getopts这是在 shell 函数中使用的简单示例:

#!/usr/bin/env bash
t() {
  local OPTIND
  getopts "a:" OPTION
  echo Input: $*, OPTION: $OPTION, OPTARG: $OPTARG
}
t "$@"
t -a foo

输出:

$ ./test.sh -a bc
Input: -a bc, OPTION: a, OPTARG: bc
Input: -a foo, OPTION: a, OPTARG: foo

正如@Adrian 指出的那样local OPTIND(或OPTIND=1)需要设置为shell 不会在多次调用()OPTIND之间自动重置。getoptsman bash

的基本语法getopts是:

getopts OPTSTRING VARNAME [ARGS...]

并且默认情况下,不指定参数等效于使用 "$@" 显式调用它,即:getopts "a:" opts "$@".

如果出现问题,这些是用于getopts检查的变量:

  • OPTIND- 要处理的下一个参数的索引,
  • OPTARG- 变量设置为由 找到的选项的任何参数getopts
  • OPTERR(不是 POSIX)- 设置为 0 或 1 以指示 Bash 是否应显示由getopts.

更多信息,请参阅:The Bash Hackers Wiki 上的小型 getopts 教程

于 2015-12-29T23:03:14.450 回答
5

参数存储在 varable 中$OPTARG

function t() {
  echo $*
  getopts "a:" OPTION
  echo $OPTION
  echo $OPTARG
}

输出:

$ t -a bc
-a bc
a
bc
于 2013-05-20T17:23:04.270 回答