在linux bash中等效于sscanf



我想提取一个出现在linux bash:脚本中间的数字

APPLES_STR="We have 123 apples."
NUM=?????

在C中,我会做一些类似的事情:

int num;
const char *str = "We have 123 apples."
sscanf(str, "We have %d apples.", &num);

如何在linux bash中做到这一点?

使用bash和正则表达式:

sscanf() {
local str="$1"
local format="$2"
[[ "$str" =~ $format ]]
}
sscanf "We have 123 apples and 42 peaches." "We have (.*) apples and (.*) peaches."

您将在字段1的数组BASH_REMATCH中找到匹配项。

echo "${BASH_REMATCH[1]}"
echo "${BASH_REMATCH[2]}"

输出:

12342

另一种类似sscanf()的方法是传入regex类型的模式进行匹配,然后使用+(...)-extglob模式用"(.*)"替换输入字符串中的所有出现,然后让[[ .. =~ .. ]]填充BASH_REMATCH,而不必传递手动插入"(.*)"的字符串的副本。例如:

#!/bin/bash
shopt -s extglob
sscanf () {
local regex="$2"
local str="${1//+(${regex})/(.*)}"
[[ $1 =~ $str ]]
}
sscanf "We have 123 apples and 42 peaches." "[[:digit:]]"
declare -p BASH_REMATCH

这基本上就是@Cyrus的伟大回答所表明的,这只是构建搜索字符串的另一种方法。

示例输出

$ bash sscanf.sh
declare -ar BASH_REMATCH=([0]="We have 123 apples and 42 peaches." [1]="123" [2]="42")

(注意:无耻地借用@Cyrus的示例文本(

最新更新