Сравнение File1 и File2 для комментирования совпадающего шаблона в File2

Это вполне возможно. При регистрации обработчика прерывания драйвер сообщает ядру адрес функции, которую следует вызывать при срабатывании прерывания. Драйвер может настроить столько прерываний, сколько пожелает, и все они могут указывать на одну и ту же процедуру обслуживания или все они могут указывать на свои собственные (или на какую-то другую комбинацию вещей).

См. этот ответ для более подробной информации о том, как на самом деле обрабатываются прерывания.

0
08.08.2017, 02:38
3 ответа

Откровенно говоря, я бы сделал это в интерактивном режиме в Vim за меньшее время, чем потребовалось бы для ввода любого из приведенных выше сценариев.

vim list2

Затем прочтите список 1 вверху. (Я предполагаю, что будет легко визуально сказать, где он заканчивается и где начинается список2, поэтому нет необходимости что-либо отмечать заранее, но вы можете :1k aсначала, если хотите, чтобы исходная строка 1 списка2 была отмечен.)

:0r list1

После этой команды ваш курсор окажется в начале файла, на первом слове test1.

Нажмите *, чтобы перейти к следующему экземпляру слова под курсором. (Это будет строка, которую вы хотите прокомментировать.)

Нажмите I, чтобы войти в режим вставки (для первого символа, отличного от -, пробела в строке, поскольку вы использовали заглавную I, а не строчную ), и напечатали //, а затем нажмите Побег.

Нажмите n, чтобы перейти к следующему экземпляру искомого слова. (Поскольку вы находитесь в начале строки сразу после ваших //символов, ваш курсор перейдет к экземпляру, который вы только что нашли. Поэтому нажмите ее еще раз, чтобы перейти к следующему экземпляру.)

Предполагая, что нужно прокомментировать только один экземпляр, вы снова окажетесь в начале файла — в первой строке.Нажмите j, чтобы перейти вниз (, или просто нажмите Enter, чтобы перейти к первому символу, отличному от -, пробела в следующей строке — тот же результат в данном случае ).

Нажмите *, чтобы перейти к следующему экземпляру test3, так как он находится под вашим курсором.

Нажмите ., чтобы повторить действие «закомментировать строку». Команда точки просто великолепна.:)

Нажмите nеще раз. (Дважды. )В вашем примере текста вы закончили — вы вернулись ко второй строке, test3. Если нужно было прокомментировать больше строк, снова просто введите j*.nn. И если есть другой, снова введите j*.nn.

Когда закончите (вы находитесь на test3или где бы ни была последняя строка из list1, чуть выше исходной первой строки из list2), нажмите dgg, чтобы удалить все строки из текущей строки в первую строку файла, чтобы записей list1там больше не было.

Всего вы вводите

vim list2<Enter>

, чтобы открыть файл, затем:

:0r list1<Enter>
*I//<Esc>nn
j*.nn
j*.nn
j*.nn
(Repeat however many times)
dgg

Затем, чтобы сохранить и выйти, введите :xи нажмите Enter.


РЕДАКТИРОВАТЬ:

Я узнал, что ваш "list1" огромен. Не имеет значения; просто используйте макрос.

Выполнив описанное выше несколько раз, чтобы убедиться, что это работает, введите:

qkj*.nnq

Это запишет j*.nnкак макрос в регистр k.

Запустите макрос, набрав @k.

Запустите его еще раз, набрав @@.

Затем запустите его 4000 раз, набрав 4000@@. Но лично я бы делал это небольшими порциями. И, возможно, не использовать команду точки в макросе, а явно ввести I//<Esc>.

Суть в том, что я бы по-прежнему делал это интерактивно, и это по-прежнему занимало всего минуту или две, независимо от того, сколько строк мне приходилось обрабатывать. Магия Вима.:)

1
28.01.2020, 02:16

Алгоритм:

 for each line of List2
     if line matches ANY pattern in List1 then
         print //line
     else
         print line

Вот реализация в bash (или аналогичном):

 while read line ;do
     if echo $line | fgrep -f List1 >/dev/null ;then
         echo "//$line"
     else
         echo "$line"
     fi
 done < List2
0
28.01.2020, 02:16

Использование awk:

$ awk -F'[".]' 'NR==FNR{a[$0]; next} $2 in a{$0="//"$0} 1' list1 list2
//'include "test1.sv"
'include "test2.sv"
//'include "test3.sv"
'include "test4.sv"

Как это работает:

  • -F'[".]'

    Это указывает awk разделять поля всякий раз, когда встречается "или ..

  • NR==FNR{a[$0]; next}

    При чтении первого файла, list, это говорит awk создать ключ в ассоциативном массиве a, равный текущей строке, а затем пропустить остальные команды и перейти к строке next.

    Подробнее:NR— это общее количество строк, которые awk уже прочитал. FNR— количество строк, прочитанных до сих пор из текущего файла. Это, когда FNR==NR, мы читаем первый файл.

  • $2 in a{$0="//"$0}

    При чтении второго файла это указывает awk добавить //в начало строки, если второе поле в текущей строке является ключом в ассоциативном массиве a.

  • 1

    Это загадочное сокращение awk для печати -строки -.

Расширенный пример

Использование дополнительной строки, упомянутой в комментариях:

$ cat list1
test1
test3
usb30_suspend_resume
$ cat list2
'include "test1.sv"
'include "test2.sv"
'include "test3.sv"
'include "usb30_suspend_resume.sv"
'include "test4.sv"
$ awk -F'[".]' 'NR==FNR{a[$0]; next} $2 in a{$0="//"$0} 1' list1 list2
//'include "test1.sv"
'include "test2.sv"
//'include "test3.sv"
//'include "usb30_suspend_resume.sv"
'include "test4.sv"

Адаптация для файлов pastebin

Файлы в pastebin имеют конечные пробелы в list1, и оба файла имеют окончание строки -в стиле окон -. Для обработки этого формата используйте:

awk 'NR==FNR{a[$1]; next} $2 in a{$0="//"$0} 1' FS='[[:space:]]' list1.txt FS='[".]' list2.txt
4
28.01.2020, 02:16

Теги

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