Невозможно добавить элементы из цикла while в пустой массив в bash

Я прочитал некоторые записи по этому вопросу, например, в здесь или здесь, но мне не удалось заставить мой код работать. Это должно быть очень просто.

Мне нужно добавить элементы из цикла while после небольшого преобразования в пустой список. Мой код выглядит следующим образом:

folder='/path/to/directories/'

ls  $folder | while read dir ; do
    if [[ $dir =~ ANF-* ]]; then
        names=()

        ls $folder/$dir/FASTQS  | while read file ; do
            name=$(echo $file | cut -d "_" -f 1-3 )
            echo $name
            names+=("$name")
        done
        echo ${names[*]}   #Also tried echo ${names[@]}
    fi
done

Первое «эхо» работает, поэтому оно проходит через условное выражение и во второй цикл.

Я также попытался использовать «объявить -a» для создания пустого массива.

Если я попытаюсь добавить $file в список, это тоже не сработает.

Я думаю, что проблема заключается в добавлении действия, потому что, если я создаю непустой массив, я получаю элементы массива во втором «эхе».

Заранее большое спасибо. RX

См. также БашFAQ/024.

Benjamin W. 14.03.2019 13:56

В качестве примечания, вместо использования ls (вывод которого заведомо хрупкий), вы должны использовать globs: for dir in "$folder"/*; do, который решает проблему установки переменной в подпроцессе. а также устойчив к именам файлов.

Benjamin W. 14.03.2019 13:57

Кроме того, ANF-* как регулярное выражение означает ANF, ANF-, ANF--, ANF--- и т. д., что, вероятно, не то, что вы имели в виду. Если вы имели в виду «начинается с ANF-», вы должны были использовать ^ANF-.* (.* для «любого числа любого символа») или просто ^ANF-, потому что =~ проверяет подсовпадения; или [[ $dir == ANF-* ]] (шаблоны оболочки вместо регулярного выражения).

Benjamin W. 14.03.2019 14:00

И, наконец, я не думаю, что вам нужен вложенный цикл; вы можете сделать что-то вроде for file in "$folder"/ANF-*/FASTQS/*; do, и в зависимости от того, как выглядят имена файлов, вы, вероятно, могли бы использовать расширение параметра для получения нужных частей.

Benjamin W. 14.03.2019 14:03

Я попробую, но я не думаю, что это проблема, я попал в цикл, и я получаю файлы, которые меня интересуют, модифицированные, проблема заключается в добавлении имен в список.

Rachael 14.03.2019 14:08

Вы меняете names в подпроцессе (внутренний | while read создает его), затем вы получаете доступ к names вне этого подпроцесса (echo ${names[*]}), но все изменения внутри подпроцесса исчезают. Самое простое исправление — изменить ls [...] | while read file; do [...]; done на while read file; do [...]; done < <(ls [...]), но обратите внимание, что при этом по-прежнему используется множество антишаблонов, таких как использование вывода ls программно.

Benjamin W. 14.03.2019 14:32
Структурированный массив Numpy
Структурированный массив Numpy
Однако в реальных проектах я чаще всего имею дело со списками, состоящими из нескольких типов данных. Как мы можем использовать массивы numpy, чтобы...
T - 1Bits: Генерация последовательного массива
T - 1Bits: Генерация последовательного массива
По мере того, как мы пишем все больше кода, мы привыкаем к определенным способам действий. То тут, то там мы находим код, который заставляет нас...
Что такое деструктуризация массива в JavaScript?
Что такое деструктуризация массива в JavaScript?
Деструктуризация позволяет распаковывать значения из массивов и добавлять их в отдельные переменные.
0
6
1 125
1

Ответы 1

Попробуйте заключить эхо в двойные кавычки:

folder='/path/to/directories/'

ls  $folder | while read dir ; do
    if [[ $dir =~ ANF-* ]]; then
        names=()
        local iteration=1
        ls $folder/$dir/FASTQS  | while read file ; do
            name=$(echo $file | cut -d "_" -f 1-3 )
            echo $name
            names+=("$name")
            echo "iteration $iteration"
            iteration=$((iteration+1))
            declare -p names
        done
        echo "${names[@]}"
        # you can show the array like this:
        declare -p names
    fi
done

Ваш массив names изменяется, но когда цикл завершается, изменения исчезают. Посмотрите на ответы @Benjamin W. любезно указал.

Большое спасибо, но я добавил ваши модификации, но они все еще не работают. Элементы цикла не добавляются в список. Цикл работает. Я получаю список файлов интересующих меня каталогов и могу изменять имена внутри цикла.

Rachael 14.03.2019 14:00

Цитирование не имеет к этому никакого отношения; проблема заключается в изменении переменной в подоболочке.

Benjamin W. 14.03.2019 14:04

@Rachael, ваш вопрос был отредактирован модератором (@Benjamin W.), и он указывает на предыдущий ответ ... вы его проверили?

vfalcao 14.03.2019 14:04

Не модератор, а просто такой же пользователь :) И вопрос не редактировался, а помечался как дубликат.

Benjamin W. 14.03.2019 14:05

Проблема изменяется без каких-либо проблем, проблема заключается в добавлении элемента, а не в его изменении.

Rachael 14.03.2019 14:09

Другие вопросы по теме