Что является более быстрым / лучшим методом между циклом for для поиска файла и поиска файла с помощью запроса файла? - PullRequest
0 голосов
/ 23 ноября 2018

Раньше у меня был скрипт, подобный следующему

for i in $(cat list.txt)
do
  grep $i sales.txt
done

Где cat list.txt

tomatoes
peppers
onions

И cat sales.txt

Price Products
$8.88 bread
$6.75 tomatoes
$3.34 fish
$5.57 peppers
$0.95 beans
$4.56 onions

Я являюсьновичок в BASH / SHELL и после прочтения таких сообщений, как Почему использование цикла оболочки для обработки текста считается плохой практикой? Я изменил предыдущий скрипт на следующий:

grep -f list.txt sales.txt

Это последнийспособ сделать это действительно лучше, чем с помощью цикла?Сначала я думал, что это так, но потом я понял, что это, вероятно, то же самое, так как grep должен читать файл запроса каждый раз, когда он ищет другую строку в целевом файле.Кто-нибудь знает, действительно ли это лучше и почему?Если что-то лучше, я, вероятно, что-то упускаю из-за того, как grep выполняет эту задачу, но я не могу понять это.

Ответы [ 2 ]

0 голосов
/ 24 ноября 2018

Ваша вторая версия лучше, потому что:

  1. Требуется только один проход по файлу (не нужно многократных проходов, как вы думаете)
  2. В нем нет сбоев иошибки в пробелах (ваша первая попытка плохо работает для green beans или /*/*/*/*)

Совершенно нормально читать файлы исключительно в шелл-коде, когда 1. вы делаете это правильно и 2. накладные расходы незначительны, но ни один из них не относится к вашему первому примеру (за исключением того факта, что файлы в настоящее время малы).

0 голосов
/ 24 ноября 2018

Расширение моего комментария ...

Вы можете скачать исходники для grep через git с помощью:

 git clone https://git.savannah.gnu.org/git/grep.git

Вы можете увидеть в строке 96 комментария src / grep.ca:

/* A list of lineno,filename pairs corresponding to -f FILENAME
   arguments. Since we store the concatenation of all patterns in
   a single array, KEYS, be they from the command line via "-e PAT"
   or read from one or more -f-specified FILENAMES.  Given this
   invocation, grep -f <(seq 5) -f <(seq 2) -f <(seq 3) FILE, there
   will be three entries in LF_PAIR: {1, x} {6, y} {8, z}, where
   x, y and z are just place-holders for shell-generated names.  */

Что является ключом к пониманию того, что искомые шаблоны, независимо от того, поступают ли они через -e или через -f с файлом, сбрасываются в массив.Этот массив является источником поиска.перемещение по этому массиву в C будет происходить быстрее, чем ваша оболочка перебирает файлТак что это одно победит в гонке на скорость.

Кроме того, как я уже упоминал в своем комментарии, grep -f list.txt sales.txt легче читать, проще в обслуживании, и нужно вызывать только одну программу (grep).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...