簡體   English   中英

如何用 bash 中的變量替換數組元素?

[英]How to substitute array element with a variable in bash?

我有大約 10 個 arrays 像這樣:

array_1=("Mike" "George" "Sam" "1234" "5678")
array_2=("Albert" "Isabel" "Sami" "4567" "9821")
array_3=("Michel" "Tom" "Cathy" "321" "5664")
array_4=("name 1" "name 2" "name 3" "1233" "4567")
array_5=...

要獲取單個數組元素(這是必需的,因為腳本中並未使用所有元素):

name1="${array_1[0]}"
name2="${array_1[1]}"
name3="${array_1[2]}"
number1="${array_1[3]}"
number2="${array_1[4]}"

有時我想使用array_2(或3/4 ..)而不是array_1。 為了避免在名稱和數字的所有行中替換 (array_1),我希望使用簡單的變量替換,因此嘗試用不同類型的引號替換,包括:

myarray="array_1" // also tried 'array_1' and $array_1
name1="${myarray[0]}" // also tried "${$!myarray[0]}" and different quotes combinations

在這一點上,我對 bash 引用和可能的間接引用如何適用於這個例子有點困惑,到目前為止,沒有找到的答案和各種嘗試都有效,旨在看看是否有一個相當簡單的方法來解決這個問題或應該的方式此處需要更改 arrays 的使用方式。 任何提示表示贊賞。

您需要使用declare -n使myarray成為 nameref。

declare -n myarray=array_1

然后你引用它,就好像它是命名數組一樣:

$ echo "${myarray[0]}"
Mike

但是請注意,這只適用於 bash 4.3+。 Apple 對 GPL v3+ 過敏,因此 macOS 在 /bin 中附帶 3.2; 如果您使用的是 Mac,則需要安裝更新的版本(例如,使用 MacPorts 或 Homebrew)。

如果您的 bash 對於 namerefs 來說太舊了,您可以使用間接:

array=array_1
name1="${!array[0]}"
name2="${!array[1]}"
name3="${!array[2]}"
number1="${!array[3]}"
number2="${!array[4]}"

演示:

$ array=array_1
$ name1="${!array[0]}"
$ echo "$name1"
Mike
$ array=array_2
$ name1="${!array[0]}"
$ echo "$name1"
Albert

@麥克風

按照 Mark Reed 的評論繼續。
我想到了分享:
$貓“73180037.sh”
#!/bin/bash
array_1=("邁克" "喬治" "山姆" "1234" "5678")
array_2=("阿爾伯特" "伊莎貝爾" "薩米" "4567" "9821")
array_3=("米歇爾""湯姆""凱茜""321""5664")
array_4=("名稱 1" "名稱 2" "名稱 3" "1233" "4567")
數組_5=...
對於我在 {1..5}

name1=array_$i[0];
name2=array_$i[1];
name3=array_$i[2];
number1=array_$i[3];
number2=array_$i[4];
回聲 ${!name1} ${!name2} ${!name3} ${!name3} ${!number1} ${!number2}
完畢

您有點需要, 中不支持的數組數組,但這並不意味着您不能做到

這是一種快速訪問數組的骯臟方式

腳本

#!/bin/bash

# bash strict mode
set -C
set -Ee
set -T
set -u
set -o pipefail

# global array
declare -a arr=();

# get each line as an array, start from 0
function array_of_array(){
    # get the index
    declare -r index=${1:?'Error: first arg is needed'};

# each line is an array
# delimiter is comma ,
data="name surname 11, name surname 12, 123, 456
name surname 21, name surname 22, 123, 456, 789
name surname 31, name surname 32, 123, 456";

    # extract that line, start from 0
    mapfile -s $index  -t array <<< "$data";

    # delimiter is ,
    IFS=',';

    # remove space after comma
    array=${array//, /,}

    # save it in arr, a global variable
    read -a arr <<< "${array[0]}";
}


# read first line into an array
# read -a arr  <<< "$(array_of_array 0)"
array_of_array 0
echo
echo '### first ###'
echo arr: "${arr[0]}"
echo arr: "${arr[1]}"
echo arr: "${arr[2]}"
echo arr: "${arr[3]}"
echo size: "${#arr[@]}"


# read second line into an array
# read -a arr <<< "$(array_of_array 1)"
array_of_array 1
echo
echo '### second ###'
echo arr: "${arr[0]}"
echo arr: "${arr[1]}"
echo arr: "${arr[2]}"
echo arr: "${arr[3]}"
echo arr: "${arr[4]}"
echo size: "${#arr[@]}"


樣品 output


### first ###
arr: name surname 11
arr: name surname 12
arr: 123
arr: 456
size: 4

### second ###
arr: name surname 21
arr: name surname 22
arr: 123
arr: 456
arr: 789
size: 5

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM