rsync между двумя каталогами

Вы также можете обработать файл дважды, чтобы не хранить что-либо в памяти:

awk '{if(NR==FNR){c++}else if(FNR<=c-3){print}}' file file

Трюк здесь - это тест NR==FNR. NR - текущий номер строки, а FNR - текущий номер текущей строки текущего файла. Если в качестве входных данных передано несколько файлов, FNR будет равно NR только при обработке первого файла. Таким образом, мы быстро получаем количество строк в первом файле и сохраняем его как c. Поскольку «два» файла на самом деле одинаковы, теперь мы знаем количество строк, которые мы хотим, поэтому мы печатаем только, если это один из них.

Хотя вы можете подумать, что это будет медленнее, чем другое подходы, это на самом деле быстрее, так как происходит не до обработки. Все делается с помощью внутренних инструментов awk (NR и FNR), кроме одного арифметического сравнения. Я тестировал файл 50 Мбайт с миллионом строк, созданных с помощью этой команды:

for i in {500000..1000000}; do 
    echo "The quick brown fox jumped over the lazy dog $i" >> file; 
done

Как вы можете видеть, времена почти идентичны, но подход, который я здесь представил, немного быстрее первого предложения Оли (но медленнее чем другие):

$ for i in {1..10}; do ( 
    time awk '{if(NR==FNR){c++}else if(FNR<=c-3){print}}' file file > /dev/null ) 2>&1 | 
       grep -oP 'real.*?m\K[\d\.]+'; 
  done | awk '{k+=$1}END{print k/10" seconds"}'; 
0.4757 seconds

$  for i in {1..10}; do ( 
    time awk '{l[NR] = $0} END {for (i=1; i<=NR-3; i++) print l[i]}' file > /dev/null ) 2>&1 | 
        grep -oP 'real.*?m\K[\d\.]+'; 
   done | awk '{k+=$1}END{print k/10" seconds"}'; 
0.5347 seconds
3
задан 26 December 2011 в 21:21

1 ответ

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

Но эти два каталога не становятся идентичными, потому что файлы, удаленные в источнике, не удаляются по месту назначения, если вы не запрашиваете это явно. Если вы хотите, чтобы вам пришлось дополнительно использовать параметр --delete.

4
ответ дан 25 May 2018 в 15:40
  • 1
    Я бы также добавил флаг -u для «пропускать файлы, которые являются более новыми на ресивере». – roadmr 27 December 2011 в 00:28
  • 2
    @enzotib спасибо – joe1983 27 December 2011 в 04:45
  • 3
    теперь я изменил свой rysnc как rsync -avh -progress -delete -stats -exclude-from = exclude.home dir1 (source) dir2 (destination) – joe1983 27 December 2011 в 06:14

Другие вопросы по тегам:

Похожие вопросы: