Похоже, в вашей установке mint установлен kexec
.
kexec
- это системный вызов, который сообщает ядру загрузить другой образ ядра и перейти к его точке входа. Это новое ядро затем заменит старое ядро и инициализирует оборудование. По сути, это перезагрузка, за исключением того, что вы не проходите через прошивку («BIOS»), что ускоряет перезагрузку.
Если вы по какой-то причине этого не хотите (например, вам нужно изменить некоторые настройки прошивки), у вас есть два варианта:
kexec-tools
. Подстановки команд, такие как $(basename...)
и переменные, также расширяются в здесь -документах, если разделитель не заключен в кавычки. Вы должны избежать $
из $(basename...)
, а также любого $
внутри него.
Исправлена версия вашего скрипта:
for letter in {A..Z}
do cat <<- EOF > batch_${letter}.sh
#!/bin/bash
module load R/3.5.1
R_func="/home/dir/R_func"
TREAT="/home/dir/POP"
BASE="/home/dir/base"
OUTPUT="/home/dir/tmp"
for letter in {A..Z} do {
for AF in \${BASE}/${letter}*.txt_step3; do
Rscript \${R_func}P_tools.R \
--ptool \${R_func}/P_tools_linux \
--group \${AF} \
--treat \${TREAT}/pop_exclude24dup \
--out \${OUTPUT}/OUT_\$(basename \${AF%%_txt_step3})_noregress \
--binary-target F; done
}
EOF
done
На самом деле это табуляция с отступом; этот глупый веб-интерфейс превращает вкладки в пробелы, что, вероятно, нарушит <<-
, который в любой оболочке POSIX удаляет только вкладки, а не пробелы перед разделителем EOF и строки из документа здесь -.
Конструкция << EOF
... EOF
называется здесь -документом, и вы можете поместить любую строку в качестве разделителя, но обычно используется EOF
.
Проблема, с которой вы столкнулись, заключается в том, что здесь -документ действует как строка в двойных -кавычках, поэтому переменные и подстановка команд в нем расширяются при запуске cat
, они не сохраняются, как -в результирующем файле. Это, вероятно, не то, что вы хотите, так как вы установили, например. R_func
в batch_x.sh
, которое вы пишете, но ${R_func}
расширится до любого значения R_func
в генерирующем скрипте.
Вы можете предотвратить это, заключив в кавычки разделитель документа здесь -, т. е. вместо этого используйте cat << 'EOF'
. Однако это предотвращает расширение всех переменных, поэтому вы не можете расширить одну и другие, не создавая файл по частям или используя разделитель без кавычек и экранируя все переменные, кроме одной, как в Ответ дяди Билли .
Теперь, если я правильно понял вашу мысль,вы хотите создать 26 скриптов, в одном из которых каждая буква жестко -закодирована. Первый сценарий, который вы создаете (batch_A.sh
), выглядит примерно так:
module load R/3.5.1
R_func="/home/dir/R_func"
....
for AF in ${BASE}/A*.txt_step3; do
Rscript ${R_func}P_tools.R \
...
done
Вместо этого вы можете создать только один сценарий, как показано ниже, и передать ему букву в качестве аргумента командной строки. Первый аргумент командной строки доступен как"$1"
:
#!/bin/bash
module load R/3.5.1
R_func="/home/dir/R_func"
TREAT="/home/dir/POP"
BASE="/home/dir/base"
OUTPUT="/home/dir/tmp"
letter=$1
for AF in ${BASE}/${letter}*.txt_step3; do
Rscript "${R_func}P_tools.R" \
--ptool "${R_func}/P_tools_linux" \
--group "${AF}" \
--treat "${TREAT}/pop_exclude24dup" \
--out "${OUTPUT}/OUT_$(basename "${AF%%_txt_step3}")_noregress" \
--binary-target F;
done
Переменная letter
теперь будет браться из командной строки, поэтому вы можете запускать batch.sh A
для обработки файлов A
и т. д.