Как вы ищете файлы, содержащие окончания строки DOS (CRLF) с помощью grep в Linux? - PullRequest
108 голосов
/ 16 сентября 2008

Я хочу искать файлы, содержащие окончания строки DOS, с помощью grep в Linux. Примерно так:

grep -IUr --color '\r\n' .

Вышеприведенное, кажется, соответствует буквальному rn, что не является желаемым.

Вывод этого будет передан через xargs в todos для преобразования crlf в lf следующим образом

grep -IUrl --color '^M' . | xargs -ifile fromdos 'file'

Ответы [ 8 ]

140 голосов
/ 16 сентября 2008

grep, вероятно, не тот инструмент, который вам нужен для этого. Он напечатает строку для каждой соответствующей строки в каждом файле. Если, скажем, вы не хотите 10 раз запускать задачи для файла из 10 строк, то grep - не лучший способ для этого. Используя команду find для запуска файла для каждого файла в дереве, затем выполните поиск по "CRLF", чтобы получить одну строку вывода для каждого файла, который имеет окончания строки в стиле dos:

find . -not -type d -exec file "{}" ";" | grep CRLF

даст вам что-то вроде:

./1/dos1.txt: ASCII text, with CRLF line terminators
./2/dos2.txt: ASCII text, with CRLF line terminators
./dos.txt: ASCII text, with CRLF line terminators
108 голосов
/ 16 сентября 2008

Используйте Ctrl + V , Ctrl + M , чтобы ввести буквенный символ возврата каретки в строку grep. Итак:

grep -IUr --color "^M"

будет работать - если ^M есть буквальный CR, который вы вводите, как я предложил.

Если вам нужен список файлов, вы также хотите добавить опцию -l.

Объяснение

  • -I игнорировать двоичные файлы
  • -U не позволяет grep удалять символы CR. По умолчанию он будет делать это, если решит, что это текстовый файл.
  • -r рекурсивно читать все файлы в каждом каталоге.
46 голосов
/ 30 ноября 2012
15 голосов
/ 16 сентября 2008

Если ваша версия grep поддерживает -P (--perl-regexp) , тогда

grep -lUP '\r$'

можно использовать.

6 голосов
/ 06 июля 2010
# list files containing dos line endings (CRLF)

cr="$(printf "\r")"    # alternative to ctrl-V ctrl-M

grep -Ilsr "${cr}$" . 

grep -Ilsr $'\r$' .   # yet another & even shorter alternative
3 голосов
/ 23 сентября 2010

В запросе был поиск ... У меня похожая проблема ... кто-то отправил смешанную строку окончания контроля версий, так что теперь у нас есть куча файлов с 0x0d 0x0d 0x0a окончания строк. Обратите внимание, что

grep -P '\x0d\x0a'

находит все строки, тогда как

grep -P '\x0d\x0d\x0a'

и

grep -P '\x0d\x0d'

не находит строк, поэтому внутри grep может происходить что-то еще когда дело доходит до шаблонов окончания строки ... к сожалению для меня!

1 голос
/ 07 ноября 2017

Вы можете использовать команду file в unix. Он дает вам кодировку символов файла вместе с ограничителями строки.

$ file myfile
myfile: ISO-8859 text, with CRLF line terminators
$ file myfile | grep -ow CRLF
CRLF  
1 голос
/ 10 октября 2011

Если, как и я, ваш минималистический Unix не включает в себя такие тонкости, как команда file , и обратные слеши в ваших grep выражениях просто не взаимодействуют, попробуйте следующее:

$ for file in `find . -type f` ; do
> dump $file | cut -c9-50 | egrep -m1 -q ' 0d| 0d'
> if [ $? -eq 0 ] ; then echo $file ; fi
> done

Модификации, которые вы, возможно, захотите сделать, включают:

  • настройте команду find , чтобы найти только файлы, которые вы хотите сканировать
  • измените команду dump на od или любую другую имеющуюся утилиту для дампа файлов
  • подтверждает, что команда cut включает в себя как начальный и конечный пробел, так и только шестнадцатеричный символ, выводимый из утилиты dump
  • ограничить вывод dump первыми 1000 символами или около того для эффективности

Например, что-то подобное может работать для вас, используя od вместо dump :

 od -t x2 -N 1000 $file | cut -c8- | egrep -m1 -q ' 0d| 0d|0d$'
...