Python -c vs ​​python - << heredoc

Я пытаюсь запустить часть кода python в bash script, поэтому я хотел понять, что лучше всего между:

#!/bin/bash
#your bash code

python -c "
#your py code
"

VS

python - <<DOC
#your py code
DOC

Я проверил сеть, но не смог скомпилировать биты вокруг темы. Считаете ли вы, что лучше лучше другого? Если вы хотите вернуть значение из кода кода python в ваш bash script, то только heredoc?

Спасибо

Ответ 1

Основным недостатком использования документа here является то, что стандартным вводом скрипта будет документ here. Так что, если у вас есть скрипт, который хочет обрабатывать его стандартный ввод, python -c - почти единственный вариант.

С другой стороны, использование python -c '...' связывает одинарные кавычки для нужд оболочки, поэтому вы можете использовать только строки в двойных кавычках в вашем скрипте Python; вместо этого использование двойных кавычек для защиты сценария от оболочки создает дополнительные проблемы (строки в двойных кавычках подвергаются различным заменам, тогда как строки в одинарных кавычках являются буквальными в оболочке).

Кроме того, обратите внимание, что вы, вероятно, хотите также заключить в кавычки разделитель here-doc, в противном случае скрипт Python подвергается аналогичным заменам.

python - <<'____HERE'
print("""Look, we can have double quotes!""")
print('And single quotes! And 'back ticks'!')
print("$(and what looks to the shell like process substitutions and $variables!)")
____HERE

В качестве альтернативы, экранирование работает идентично, если вы предпочитаете это (python - <<\____HERE)

Ответ 2

Если вы предпочитаете использовать python -c '...', не выполняя двойные кавычки, вы можете сначала загрузить код в переменной bash, используя здесь-документы:

read -r -d '' CMD << '--END'
print ("'quoted'")
--END
python -c "$CMD"

Код python загружается дословно в CMD-переменную, и нет необходимости избегать двойных кавычек.

Ответ 3

Если вы используете bash, вы можете избежать проблем с heredoc, если примените немного больше стандартного шаблона:

python <(cat <<EoF

name = input()
print(f'hello, {name}!')

EoF
)

Это позволит вам запустить встроенный сценарий Python без отказа от стандартного ввода. Накладные расходы в основном аналогичны использованию cmda | cmdb cmda | cmdb. Этот метод известен как процесс замещения.

Если вы хотите как-то проверить скрипт, я предлагаю вам вывести его во временный файл:

#!/bin/bash

temp_file=$(mktemp my_generated_python_script.XXXXXX.py)

cat > $temp_file <<EoF
# embedded python script
EoF

python3 $temp_file && rm $temp_file

Это сохранит скрипт, если он не запустится.