Видаліть усі файли, що починаються з символу #


182

Всі рядки з коментарями у файлі починаються з #. Як я можу видалити всі рядки (і лише ті рядки), з яких починається #? Інші рядки, що містять #, але не на початку рядка, слід ігнорувати.


1
Чи має це працювати зі загальною конвенцією, яка #blah \<nl>blahвважається єдиною "логічною лінією", тому що зворотна косої лінії виходить з нового рядка?
sarnold

@sarnold: окрім того make, які утиліти використовують "зворотні рядки сплайсингу, перш ніж закінчити коментар"? Снаряди (тестування bash та ksh) не роблять. C і C ++ обробляють сплайсинг нового рядка перед іншими обробками директив препроцесора, але це директиви, а не коментарі.
Джонатан Леффлер

@Jonathan: Дивовижний. Я припускав, що спільне \<nl>втеча також буде працювати на коментарі. Але ось я помилявся. Ще не вдалося знайти іншого прикладу ... :) Дякую!
sarnold

Відповіді:


301

Це можна зробити за допомогою одношарового sed-lin :

sed '/^#/d'

Це говорить: "знайдіть усі рядки, які починаються з #, і видаліть їх, залишивши все інше".


9
скорочена версія:sed /^#/d
kev

80
Для ноубків Linux, таких як я:sed '/^#/ d' < inputFile.txt > outputFile.txt
Ніл МакГуйган

49
Найкоротший версія: sed -i '/^#/d' filepath.
лесдерід

14
А sed -i '' '/^#/d' filepathна Mac ( оскільки суфікс -i обов'язковий )
paulcm

1
@Viesturs Спробуйте це: awk '/^#/ && !first { first=1 ; next } { print $0}'
Реймонд Хеттінгер

56

Я трохи здивований, ніхто не запропонував найбільш очевидного рішення:

grep -v '^#' filename

Це вирішує проблему, як заявлено.

Але зауважте, що загальною умовою є все, що від а #до кінця рядка трактується як коментар:

sed 's/#.*$//' filename

хоча це розглядає, наприклад, #символ у рядковій літералі як початок коментаря (який може бути або не мати значення для вашого випадку) (і він залишає порожні рядки).

Рядок, що починається з довільного пробілу, після якого #також може трактуватися як коментар:

grep -v '^ *#' filename

якщо пробіл - це лише пробіли, або

grep -v '^[  ]#' filename

де два пробіли фактично є пробілом, за яким слідує буквальний символ вкладки (тип "вкладка control-v").

Для всіх цих команд пропустіть filenameаргумент для читання зі стандартного вводу (наприклад, як частина труби).


Я додав нову відповідь, яка ґрунтується на цій відповіді.
Acumenus

У мене виникли проблеми із використанням грепу таким чином у Windows. Рішення полягає в заміні "на", наприкладgrep -v "^#" filename
Serg

14

Протилежність рішення Реймонда:

sed -n '/^#/!p'

"не друкувати нічого, крім рядків, які НЕ починаються з #"


9

ви можете безпосередньо редагувати свій файл за допомогою

sed -i '/^#/ d'

Якщо ви хочете також видалити рядки коментарів, які починаються з деякого використання пробілу

sed -i '/^\s*#/ d'

Зазвичай ви хочете зберегти перший рядок свого сценарію, якщо це ша-баг, тому sedне слід видаляти рядки, починаючи з #!. також слід видалити рядки, які містять лише хеш, але не містять тексту. зібрати все це разом:

sed -i '/^\s*\(#[^!].*\|#$\)/d'

Щоб відповідати всім варіантам sed, потрібно додати -iопцію розширення резервного копіювання :

sed -i.bak '/^\s*#/ d' $file
rm -Rf $file.bak

1
плюс 1 для того, котрий простір
deepaksingh pawar


5

Ця відповідь ґрунтується на більш ранній відповіді Кіта .

egrep -v "^[[:blank:]]*#" слід фільтрувати рядки коментарів.

egrep -v "^[[:blank:]]*(#|$)" слід фільтрувати як коментарі, так і порожні рядки, як це часто корисно.

Для отримання інформації про [:blank:]та інші класи символів див. Https://en.wikipedia.org/wiki/Regular_expression#Character_classes .


Якщо припустити, що egrepпідтримує цей синтаксис; старіші версії можуть не бути.
Кіт Томпсон

-3

Ось він з циклом для всіх файлів з деяким розширенням:

ll -ltr *.filename_extension > list.lst

for i in $(cat list.lst | awk '{ print $8 }') # validate if it is the 8 column on ls 
do
    echo $i
    sed -i '/^#/d' $i
done
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.