¿Cómo puedo "cat" un archivo y eliminar líneas comentadas?


29

Me gustaría saber si hay una manera en que podría catpresentar un me gusta php.iniy eliminar todas las líneas que comienzan con;

Por ejemplo, si el archivo contiene esto:

;   - Show all errors, except for notices
;
;error_reporting = E_ALL & ~E_NOTICE
;
;   - Show only errors
;
;error_reporting = E_COMPILE_ERROR|E_ERROR|E_CORE_ERROR
;
;   - Show all errors except for notices
;
error_reporting  =  E_ALL & ~E_NOTICE

y ejecuté el comando correcto cat | {remove comments command}, luego terminaría con:

error_reporting  =  E_ALL & ~E_NOTICE

Nota - Supuse que catsería la mejor manera de hacer esto, pero estoy realmente bien con la respuesta usando otra utilidad como awk, sed, egrep, etc.


¿Qué tal algo así error_reporting = E_ALL & E_NOTICE ; Show all errors, except for notices? ¿Debería eliminarse el comentario también en ese caso?
un CVn

@ MichaelKjörling - Estoy muy bien con las líneas que acaba de empezar con los comentarios eliminándose
cwd

1
cates la herramienta para concatenar archivos. grepes la herramienta para filtrar líneas basadas en patrones. sedy awktambién puede modificar esas líneas.
Stéphane Chazelas

Respuestas:



25

No necesita canalizar un archivo a través de grep, grep toma los nombres de archivo como argumentos de línea de comando.

grep -v '^#' file1 file2 file3

imprimirá todas las líneas, EXCEPTO las que comiencen con un # char. puede cambiar el comentario char a lo que desee.

Si tiene más de un comentario char (suponiendo que esté al principio de una línea)

egrep -v '^(;|#|//)' filelist

2
Otro que he hecho que siempre me ha quedado grabado fue grep '^[^;]' filename. Sin embargo, no puedo hablar de su portabilidad.
Jodie C

@JodieC, eso es portátil pero también elimina las líneas vacías (lo que a menudo se desea). El equivalente estándar de egrepes grep -E. También se puede usargrep -ve '^[;#]' -e '^//'
Stéphane Chazelas

9

egreppuede ahorrarte el uso de cat. En otras palabras, cree menos procesos ( egrepvs cat+ egrep) y use menos buffers (canalización de cata egrepvs sin tubería).

En general, es una buena idea limitar el uso de catsi simplemente desea pasar un archivo a un comando que pueda leerlo por sí solo.

Dicho esto, el siguiente comando eliminará los comentarios, incluso si están sangrados con espacios o pestañas:

egrep -v '^ [[: en blanco:]] *;' file.ini

Es curioso que combine el nuevo formato de expresión regular de la [[ clase de caracteres ]] con el uso del egrepcomando en desuso durante al menos una década más o menos.
mikeserv

Interesante ... los documentos actuales en gnu.org/software/grep/manual/html_node/… incluyen clases POSIX.
Jack Wasey

7
egrep -v '^;|^$' $file

eso excluirá líneas que comienzan con ';' y líneas vacías.

en regex, ^indica el comienzo de una línea y $el final de una línea, por lo que ^$especifica líneas donde el carácter de inicio de línea y el carácter de final de línea están uno al lado del otro.


así que si estoy leyendo esto correctamente, ¿esto puede eliminar líneas comentadas, pero también líneas en blanco?
cwd

1
@cwd Sí. No estoy seguro de por qué incluyó ambos, pero si solo desea eliminar las líneas comentadas, simplemente useegrep -v '^;'
Michael Mrozek

44
A egrep también le gustan los archivos (se utilizan menos procesos y buffers), y una pequeña ventaja sería eliminar también los comentarios sangrados:egrep -v '^[[:blank:]]*;' file.ini
nrolans

10
Necesitamos una insignia de "uso inútil del gato".
Simon Richter

@nrolans: parece un comentario popular, ¿por qué no responderlo?
cwd

2

Una simple awkfrase awk '/^;/{next}1' input_filedebería hacer el truco.

[jaypal:~/Temp] cat file
;   - Show all errors, except for notices
;
;error_reporting = E_ALL & ~E_NOTICE
;
;   - Show only errors
;
;error_reporting = E_COMPILE_ERROR|E_ERROR|E_CORE_ERROR
;
;   - Show all errors except for notices
;
error_reporting  =  E_ALL & ~E_NOTICE

[jaypal:~/Temp] awk '/^;/{next}1' file
error_reporting  =  E_ALL & ~E_NOTICE
[jaypal:~/Temp] 

3
Correcto, pero detallado. Solo awk '!/^;/' input_filees suficiente.
manatwork

2

Además de Jaypal, probablemente también lo usaría awkpara estos fines. Es peor mencionar que Perl a veces es bastante útil para tales propósitos:

cat data.txt | perl -lne "print unless /^;/"

Las expresiones regulares de Perl son más potentes en comparación con las de awk y, a veces, es posible que las necesites.


+1 para perl, aunque el gato y el -l son redundantes, por lo que una invocación más simple esperl -ne 'print unless /^;/' data.txt
Simon Whitaker

@Simone Whitaker, sí, tienes razón: es solo un hábito escribirlo como yo lo hago, y vale la pena mencionarlo.
shabunc

1
Cosa segura. De hecho, creo que catfunciona bien en estos ejemplos si lo considera como un proxy para el más genérico "cualquier cosa que genere texto en STDOUT". Las pipas Unix son lo mejor desde el pan rebanado, en mi humilde opinión. :)
Simon Whitaker

2

Una elaboración de la respuesta de @ shabunc, que usa Perl para eliminar comentarios (incluidos los comentarios en línea), luego imprime cualquier línea que contenga algo que no sea espacio en blanco.

$ perl -ne 's/;.*//; print if /\S/' data.txt

Explicación:

  • s/;.*//usa el operador de sustitución ( s/<regex>/<replacement>/) para reemplazar las instancias de un punto y coma y todo lo que sigue en una línea con la cadena vacía.
  • print if /\S/imprime la línea si coincide con la expresión regular \S, que es una clase de caracteres que coincide con todos los caracteres que no son espacios en blanco.

1

Aquí hay uno que uso, solo sustituyo ';' con el carácter de comentario (por ejemplo, '#' para muchos archivos de configuración del servicio UNIX):

grep -Ev '^[[:space:]]*;|^$' chan_dahdi.conf.sample | sed 's/;.*$//'

Eso elimina todos los comentarios de línea completa (incluso si tienen espacios en blanco iniciales), y cualquier comentario que finalice las líneas sin comentarios, y también elimina sucintamente las líneas en blanco de la salida. Esto puede ser posible sin la tubería (mi sed o awk-fu no es genial), pero es tan fácil de entender (y recordar), pensé que lo publicaría aquí.


1

Ejemplo mostrar solo líneas + no mostrar nuevas líneas o líneas vacías:

$ egrep -v '^(;|#|//)' /etc/ssh/sshd_config | tr '\n' ' '

 Protocol 2    SyslogFacility AUTHPRIV      PasswordAuthentication yes  ChallengeResponseAuthentication no   GSSAPIAuthentication yes GSSAPICleanupCredentials yes  UsePAM yes  AcceptEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES AcceptEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT AcceptEnv LC_IDENTIFICATION LC_ALL LANGUAGE AcceptEnv XMODIFIERS  X11Forwarding yes   Subsystem sftp    /usr/libexec/openssh/sftp-server 

O

$ egrep -v '^(;|#|//|$)' /etc/ssh/sshd_config    

Protocol 2
SyslogFacility AUTHPRIV
PasswordAuthentication yes
ChallengeResponseAuthentication no
GSSAPIAuthentication yes
GSSAPICleanupCredentials yes
UsePAM yes
AcceptEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES
AcceptEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT
AcceptEnv LC_IDENTIFICATION LC_ALL LANGUAGE
AcceptEnv XMODIFIERS
X11Forwarding yes
Subsystem   sftp    /usr/libexec/openssh/sftp-server

2
El uso de egrepestá en desuso por mucho tiempo. grep -Ees el comando que estás buscando aquí.
mikeserv

0
egrep -v ^'(#|$)' file.txt

Elimina todos los comentarios y líneas vacías de file.txt


2
Debería considerar expandir su respuesta con un poco más de información para los no iniciados (por ejemplo, exactamente lo que hace la expresión regular que usa).
HalosGhost

egrepes depreciado Usar en su grep -Evlugar.
Yokai


0

puede usar el siguiente comando para guardar las líneas, excluyendo las líneas vacías y las líneas que comienzan con # en un archivo nuevo

cat <file to be read> | egrep -v '^#|^$' > <file to be written at>


catTubería inútil y egrepse deprecia y se reemplaza porgrep -E por expresiones extendidas o simplemente grep -v.
Yokai
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.