Использование подстановки параметров в массиве Bash

fdisk -l или sfdisk -l сделает свое дело, а blkid yourdevice может предоставить вам информацию о типе, uid и файловой системе на вашем устройстве

8
26.03.2019, 17:44
5 ответов

Я бы удалил то, что нужно удалить с помощьюsedперед загрузкой в ​​массив (также обратите внимание на имена переменных в нижнем регистре, вообще лучше избегать использования переменных с заглавной буквы в сценариях оболочки):

#!/bin/bash
readarray -t array< <(sed 's/"//g; s/  *//g; s/,/"/; s/,//g; s/"/,/' "$1")
for element in "${array[@]}";do
    echo "|ELEMENT|$element|"
done

Это приводит к следующему результату в файле примера:

$ foo.sh file 
|ELEMENT|10,this|
|ELEMENT|20,is|
|ELEMENT|30,all|
|ELEMENT|40,I|
|ELEMENT|50,need2|
|ELEMENT|60,see|

Если вам действительно необходимо использовать подстановку параметров, попробуйте что-то вроде этого:

#!/bin/bash
readarray -t array< "$1"
array=( "${array[@]// /}" )
array=( "${array[@]//\"/}" )
array=( "${array[@]/,/\"}" )
array=( "${array[@]//,/}" )
array=( "${array[@]/\"/,}" )

for element in "${array[@]}"; do
    echo "|ELEMENT|$element|"
done
9
27.01.2020, 20:08
ELEMENT='50,n,e,e,d,2'
IFS=, read -r first rest <<<"$ELEMENT"
printf "%s,%s\n" "$first" "${rest//,/}"
50,need2

Избавьтесь от привычки использовать имена переменных ALLCAPS. В конечном итоге вы столкнетесь с важной «системной» переменной, такой как PATH, и сломаете свой код.

9
27.01.2020, 20:08

Вы можете перебрать массив и использовать промежуточную переменную:

for((i=0; i < "${#ARRAY[@]}"; i++))
do
  rest="${ARRAY[i]#*,}"
  ARRAY[i]="${ARRAY[i]%%,*}","${rest//,/}"
done

Это присваивает restчасть после первой запятой; затем мы объединяем три части обратно в исходную переменную:

  • часть до первой запятой
  • запятая
  • замена в restкаждой запятой ничем
6
27.01.2020, 20:08

Насколько я понимаю, нет необходимости читать его в массив bashдля создания этого вывода:

$ sed 's/[ "]//g; s/,/ /; s/,//g; s/ /,/; s/.*/|ELEMENT|&|/' <file
|ELEMENT|10,this|
|ELEMENT|20,is|
|ELEMENT|30,all|
|ELEMENT|40,I|
|ELEMENT|50,need2|
|ELEMENT|60,see|

Выражение sedудаляет пробелы и двойные кавычки, заменяет первую запятую пробелом (в этой точке в строке нет других пробелов ), удаляет все остальные запятые, восстанавливает первую запятую и добавляет и добавляет дополнительные данные.

Как вариант, с GNUsed:

sed 's/[ "]//g; s/,//2g; s/.*/|ELEMENT|&|/' <file
Стандарт

(sedне поддерживает комбинацию 2и gв качестве флагов для команды s).

10
27.01.2020, 20:08

[По сути, это более полная версия ответа Гленна Джекмана ]

Построение ассоциативного массива из разделенных ключа и значения с использованием первой запятой в качестве разделителя:

declare -A arr
while IFS=, read -r k v; do arr["${k//[ \"]}"]="${v//[,\"]}"; done < file.txt
for k in "${!arr[@]}"; do 
  printf '|ELEMENT|%s,%s|\n' "$k" "${arr[$k]}"
done
|ELEMENT|20,is|
|ELEMENT|10,this|
|ELEMENT|50,need2|
|ELEMENT|40,I|
|ELEMENT|60,see|
|ELEMENT|30,all|
8
27.01.2020, 20:08

Теги

Похожие вопросы