awk error de declaración if-then-else

Estoy escribiendo una declaración if-then-else usando awk en un script bash.

Lo que me gustaría hacer es identificar líneas con valores de columna 1 que no coincidan con una cadena en particular (rs o chr) y agregar un prefijo (chr) a los valores de columna 1 para esas líneas identificadas. Todas las líneas con la cadena coincidente deben imprimirse como estaban, sin agregar.

Mi línea de código hasta ahora es:

awk "{if (! ($1 ~ /rs/ || $1 ~ /chr/)) {($1 == "chr"$1); print $0}}; else {print $0}" filename > newfilename 

I sigo recibiendo mensajes de error de sintaxis con este código.

Puedo realizar la identificación y la adición con éxito por su cuenta, pero tengo problemas para combinarlos en un solo comando.

Comentarios

  • verifique dónde cierra el segundo corchete: '{ if ( this is given) { do this } else { do that } }'

Respuesta

Aquí está su código, ampliado para mayor visibilidad:

awk " { if (! ($1 ~ /rs/ || $1 ~ /chr/) ) { ($1 == "chr"$1); print $0} }; else { print $0 } " filename > newfilename 

Hay una serie de problemas con esto que me vienen a la mente

  1. Estás usando una comparación de igualdad en lugar de una asignación para probar y agregue el prefijo chr
  2. Ha puesto lo que debería ser una asignación entre corchetes
  3. Hay un } después del primer
  4. No debe haber punto y coma antes de la else parte
  5. Te falta el cierre final } después del código

Aquí hay una versión fija, aún expandida:

awk " { if (! ($1 ~ /rs/ || $1 ~ /chr/) ) { $1 = "chr" $1; print $0 } else { print $0 } } " filename > newfilename 

Y luego podemos ver una optimización simple para mover el print $0 repetido fuera de su condición:

awk " { if (! ($1 ~ /rs/ || $1 ~ /chr/) ) { $1 = "chr" $1 } print $0 } " filename > newfilename 

Dado que Esto es básicamente una simple «condición → enmendar». De hecho, puede usar la estructura estándar de awk «para simplificar esto aún más. Aquí tenemos dos awk declaraciones, procesadas secuencialmente para cada línea de su archivo de entrada. La primera línea tiene el prefijo "chr" según sea necesario. El segundo imprime cada línea.

awk " (! ($1 ~ /rs/ || $1 ~ /chr/) ) { $1 = "chr" $1 } 1 " filename > newfilename 

Como es awk, incluso se puede enrollar en una sola línea , aunque la legibilidad sufre un poco

awk "(! ($1 ~ /rs|chr/) ) { $1 = "chr" $1 } 1" filename > newfilename 

Respuesta

El uso de esta línea parece funciona perfectamente:

awk "!($1 ~ /rs/ || /chr/) {$1="chr"$1}1" 

Comentarios

  • ($1 ~ /rs/ || /chr/) coincidirá con $1 para "rs", pero $0 para "chr". Debes ($1 ~ /rs/ || $1 ~ /chr/) o ($1 ~ /rs|chr/)

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *