Как проверить, существует ли строка в файле с Bash?
У меня есть файл, который содержит имена каталогов:
my_list.txt
:
/tmp
/var/tmp
Я хотел бы проверить в Bash, прежде чем я добавлю имя каталога, если это имя уже существует в файле.
11 ответов
grep -Fxq "$FILENAME" my_list.txt
Статус выхода равен 0 (true), если имя найдено, 1 (false), если нет, поэтому:
if grep -Fxq "$FILENAME" my_list.txt
then
# code if found
else
# code if not found
fi
Вот соответствующие разделы справочной страницы дляgrep
:
grep [options] PATTERN [FILE...]
-F, --fixed-strings
Interpret PATTERN as a list of fixed strings, separated by new-
lines, any of which is to be matched.
-x, --line-regexp
Select only those matches that exactly match the whole line.
-q, --quiet, --silent
Quiet; do not write anything to standard output. Exit immedi-
ately with zero status if any match is found, even if an error
was detected. Also see the -s or --no-messages option.
Относительно следующего решения:
grep -Fxq "$FILENAME" my_list.txt
В случае, если вам интересно (как я), что -Fxq
означает на простом английском:
F
: Влияет на интерпретацию PATTERN (фиксированная строка вместо регулярного выражения)x
: Соответствовать всей линииq
: Тссс... минимальная печать
Из файла man:
-F, --fixed-strings
Interpret PATTERN as a list of fixed strings, separated by newlines, any of which is to be matched.
(-F is specified by POSIX.)
-x, --line-regexp
Select only those matches that exactly match the whole line. (-x is specified by POSIX.)
-q, --quiet, --silent
Quiet; do not write anything to standard output. Exit immediately with zero status if any match is
found, even if an error was detected. Also see the -s or --no-messages option. (-q is specified by
POSIX.)
Три метода в моей голове:
1) Короткий тест для имени в пути (я не уверен, что это может быть ваш случай)
ls -a "path" | grep "name"
2) Короткий тест для строки в файле
grep -R "string" "filepath"
3) Более длинный скрипт bash с использованием регулярных выражений:
#!/bin/bash
declare file="content.txt"
declare regex="\s+string\s+"
declare file_content=$( cat "${file}" )
if [[ " $file_content " =~ $regex ]] # please note the space before and after the file content
then
echo "found"
else
echo "not found"
fi
exit
Это должно быть быстрее, если вам нужно протестировать несколько строк в содержимом файла, используя цикл, например, изменить регулярное выражение в любом цикле.
Самый простой и простой способ будет:
isInFile=$(cat file.txt | grep -c "string")
if [ $isInFile -eq 0 ]; then
#string not contained in file
else
#string is in file at least once
fi
grep -c вернет счетчик того, сколько раз строка встречается в файле.
Более простой способ:
if grep "$filename" my_list.txt > /dev/null
then
... found
else
... not found
fi
Совет: отправьте /dev/null
если вы хотите статус выхода команды, но не выходы.
Вот быстрый способ поиска и оценки строки или части строки:
if grep -R "my-search-string" /my/file.ext
then
# string exists
else
# string not found
fi
Вы также можете сначала проверить, возвращает ли команда какие-либо результаты, только выполнив:
grep -R "my-search-string" /my/file.ext
grep -E "(string)" /path/to/file || echo "no match found"
-E опция заставляет grep использовать регулярные выражения
Если я правильно понял ваш вопрос, это должно сделать то, что вам нужно.
- Вы можете указать каталог, который хотите добавить через переменную $ check
- если каталог уже находится в списке, вывод "dir уже в списке"
- если каталога еще нет в списке, он добавляется в my_list.txt
В одной строке: check="/tmp/newdirectory"; [[ -n $(grep "^$check\$" my_list.txt) ]] && echo "dir already listed" || echo "$check" >> my_list.txt
Решение @Thomas по какой-то причине у меня не сработало, но у меня была более длинная строка со специальными символами и пробелами, поэтому я просто изменил параметры следующим образом:
if grep -Fxq 'string you want to find' "/path/to/file"; then
echo "Found"
else
echo "Not found"
fi
Надеюсь, это кому-то поможет
Моя версия с использованием fgrep
FOUND=`fgrep -c "FOUND" $VALIDATION_FILE`
if [ $FOUND -eq 0 ]; then
echo "Not able to find"
else
echo "able to find"
fi
Если вы просто хотите проверить наличие одной строки, вам не нужно создавать файл. Например,
if grep -xq "LINE_TO_BE_MATCHED" FILE_TO_LOOK_IN ; then
# code for if it exists
else
# code for if it does not exist
fi
Я искал способ сделать это в терминале и отфильтровать строки в обычном "поведении grep". Храните свои строки в файле
strings.txt
:
string1
string2
...
Затем вы можете создать регулярное выражение, например
(string1|string2|...)
и использовать его для фильтрации:
cmd1 | grep -P "($(cat strings.txt | tr '\n' '|' | head -c -1))" | cmd2
Немного похож на другие ответы, но не разветвляется
cat
и записи могут содержать пробелы
contains() {
[[ " ${list[@]} " =~ " ${1} " ]] && echo 'contains' || echo 'does not contain'
}
IFS=$'\r\n' list=($(<my_list.txt))
Итак, для
my_list.txt
нравиться
/tmp
/var/tmp
/Users/usr/dir with spaces
эти тесты
contains '/tmp'
contains '/bin'
contains '/var/tmp'
contains '/Users/usr/dir with spaces'
contains 'dir with spaces'
возвращение
exists
does not exist
exists
exists
does not exist
grep -Fxq "String to be found" | ls -a
- grep will поможет вам проверить содержимое
- ls перечислит все файлы
Решение без grep, работает для меня:
MY_LIST=$( cat /path/to/my_list.txt )
if [[ "${MY_LIST}" == *"${NEW_DIRECTORY_NAME}"* ]]; then
echo "It's there!"
else
echo "its not there"
fi
на основании: /questions/33095505/kak-proverit-soderzhit-li-stroka-podstroku-v-bash/33095548#33095548
if grep -q "$Filename$" my_list.txt
then
echo "exist"
else
echo "not exist"
fi