Вы создали переменную с именем _now
, но позже ссылаетесь на переменную с именем _nowout
. Чтобы избежать подобных проблем, используйте фигурные скобки для разделения имен переменных:
_now=$(date +"%m_%d_%Y")
_file="${_now}out.log"
touch "$_file.txt"
Обратите внимание, что я оставил "$_file.txt"
как есть, потому что .
уже является разделителем имен переменных. Если есть сомнения, можно использовать "${_файл}.txt"
.
Бонус 1: ${varname}
синтаксис на самом деле обеспечивает несколько полезных строковых операций над переменными, в дополнение к разграничению.
Бонус 2: для разграничения имен переменных можно также использовать творческое экранирование и кавычки оболочки. Можно заключить в кавычки переменную и строковый литерал отдельно (например, file="$_now""out.log"
или file="$_now"'out.log'
) или оставить одну из частей без кавычек (например, file=$_now "out.log"
или file="$_now "out.log
). Наконец, вы можете экранировать один символ, который следует за именем переменной: file=$_now\out.log
. Хотя я бы не рекомендовал повторно использовать эти примеры без хорошего понимания правил цитирования и экранирования shell.
Если вы должны сделать это из find, вам нужно вызвать оболочку:
find./ -type f -name "*.txt" -exec sh -c 'grep -EiH something "$1" | grep -E somethingelse | grep -E other' sh {} \;
Другие альтернативы включают использование xargs
вместо:
find./ -type f -name "*.txt" |
xargs -I{} grep -EiH something {} |
grep -EiH somethingelse |
grep -EiH other
Или, что намного безопаснее для произвольных имен файлов (, если ваш find
поддерживает-print0
):
find./ -type f -name "*.txt" -print0 |
xargs -0 grep -EiH something {} |
grep -Ei somethingelse |
grep -Ei other
Или вместо этого вы можете просто использовать цикл оболочки:
find./ -type f -name "*.txt" -print0 |
while IFS= read -d '' file; do
grep -Ei something "$file" |
grep -Ei somethingelse |
grep -Ei other
done
Изменить :Этот ответ не предпочтителен , но оставлен здесь для сравнения и иллюстрации потенциально опасных ловушек в сценариях bash.
Вы можете указатьbash
(или другую оболочку )в качестве команды -exec
:
find -type -f -name "*.txt" -exec bash -c 'egrep -iH something "{}" | egrep somethingelse | egrep other' \;
Одним из недостатков этого способа является то, что он создает больше возможностей для проблем с вложенными кавычками по мере того, как ваши команды становятся более сложными. Если вы хотите избежать этого, вы можете разбить его на циклfor
-:
for i in $(find -type -f -name "*.txt"); do
if egrep -iH something "$i" | egrep somethingelse | egrep other; then
echo "Found something: $i"
fi
done