首页 > 解决方案 > 从文字变量输入创建序列

问题描述

我正在尝试按如下方式创建序列:

startDay=1
endDay=2
dayRange="{$startDay..$endDay}"
echo \[\"$dayRange\",\"{00..02}\"\]

输出是:

["{1..2}","00"] ["{1..2}","01"] ["{1..2}","02"]

直接指定序列时{00..02},它会自动创建"00", "01", "02",但它不理解dayRange变量。我期望它返回的是:

["1","00"] ["1","01"] ["1","02"] ["2","00"] ["2","01"] ["2","02"] 

不知道我错过了什么。请指教。

标签: linuxbashshellbrace-expansion

解决方案


第一个想法是一个简单的嵌套for循环:

startDay=1
endDay=2

pfx=
out=

for ((i=startDay; i<=endDay; i++))
do
    for j in {00..02}
    do
         out+="${pfx}[\"${i}\",\"${j}\"]"
         pfx=" "
    done
done

echo "${out}"

这会产生:

["1","00"] ["1","01"] ["1","02"] ["2","00"] ["2","01"] ["2","02"]

编码少一点,速度快一点,它使用 OPecho ... {00..02}来消除其中一个for循环:

注意:这消除了$(echo ...)我在之前编辑中的子进程调用。

startDay=1
endDay=2

for ((i=startDay; i<=endDay; i++))
do
    echo -n "[\""${i}"\",\""{00..02}"\"]"
    echo -n " "
done

echo ""

这也会产生:

["1","00"] ["1","01"] ["1","02"] ["2","00"] ["2","01"] ["2","02"]

这是一个awk想法:

awk -v start=$"${startDay}" -v end="${endDay}" '
BEGIN {
    pfx=""
    out=""

    for (i=start; i<=end; i++)
        for (j=0; j<=2; j++) {
             out=out pfx "[\"" i "\",\"" sprintf("%02d", j) "\"]"
             pfx=" "
        }
    print out
}'

这也会产生:

["1","00"] ["1","01"] ["1","02"] ["2","00"] ["2","01"] ["2","02"]

随着早期子进程的消除,$(echo ...)前 2 个解决方案采用个位数毫秒计时,而awk解决方案采用低两位数毫秒计时。

随着天数(和/或序列大小)的增加,前 2 个解决方案开始花费更长的时间(嵌套for循环落后得更远),而awk解决方案往往保持相同的速度。

对于非常大的增长(天数和/或序列大小),我希望awk能够接近并最终占据领先地位。


推荐阅读