Получить строки только с определенными полями

#CHROM  POS     T1      T10     T11     T12     T13     T2      T3      T4      T5      T6      T106    T107    T108    T109    T110    T112    T114    T116    T120    T122    T125    T128    T129    T130
Aradu.A01       300806  H       B       B       B       B       B       B       B       H       B       B       H       B       B       B       B       B       B       B       B       B       B       B
Aradu.A01       386907  A       A       A       A       A       A       A       A       A       A       A       A       H       A       A       A       A       A       H       A       A       A       A
Aradu.A01       463100  B       B       A       A       A       A       A       H       B       A       A       H       H       H       H       H       B       A       B       A       H       H       A
Aradu.A01       471639  A       A       A       A       H       A       A       H       A       A       H       A       A       A       A       A       H       A       A       A       H       A       A
Aradu.A01       644024  H       B       B       B       B       B       B       B       H       H       B       H       H       B       B       B       H       B       H       B       B       B       H
Aradu.A01       756331  H       H       H       H       H       H       H       H       B       B       B       H       H       H       H       H       B       H       H       H       B       B       B
Aradu.A01       768081  A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A       A
Aradu.A01       783066  A       A       H       A       H       H       A       A       A       A       H       A       H       A       A       A       A       A       A       H       A       A       H
Aradu.A01       812865  H       B       H       H       H       H       H       H       H       H       H       H       H       H       H       H       B       B       H       H       B       B       H
Aradu.A01       976731  A       H       A       H       H       A       H       H       A       H       H       A       H       H       A       A       H       A       H       A       A       A       H
Aradu.A01       1089311 A       H       H       H       H       A       A       A       H       A       H       B       A       H       H       H       H       H       A       A       H       H       H
Aradu.A01       1089991 A       A       A       H       A       A       H       A       A       H       A       A       A       A       H       A       A       A       A       A       A       A       H
Aradu.A01       1113781 H       H       H       H       H       H       H       A       H       H       H       H       H       H       A       H       H       A       H       A       H       H       H
Aradu.A01       1160441 B       B       B       B       B       B       H       B       H       B       B       B       B       B       H       B       B       B       B       B       B       B       B
Aradu.A01       1638873 B       H       B       B       H       B       B       B       B       B       B       B       H       H       H       B       B       B       B       B       H       B       B
Aradu.A01       1638907 B       H       B       B       H       B       B       B       H       B       B       B       H       H       H       B       B       B       B       B       H       B       B

Кто-нибудь, пожалуйста, помогите мне с кодом awk, который может получить только строки, в которых есть поля с буквой "A" а "Б" в нем? Строки с
1) только «А» и «Н»,
2) только "B" и "H" НЕ учитываются.

Каждый должен иметь как A, так и B. Если H также присутствует с A и B, тогда также следует учитывать строку. Таким образом, необходимо иметь только строки с «A» и «B», и если «H» присутствует вместе с «A» и «B», то эту строку также следует учитывать:

NR>1  {for(i=3;i<=NF;i++)
        { if ( $i ~ "A" && $i ~ "B" && $1 ~ "H" ) ;
       } ## if ;
       ## for loop is done
       print ;

Приведенный выше код возвращает результат файл в качестве входного файла. }

0
06.01.2017, 19:13
2 ответа

Не решение awk , но этот grep , похоже, помогает:

egrep '^Aradu\.[A-Z][0-9]{2}.*A.*B|^Aradu\.[A-Z][0-9]{2}.*B.*A' aradu
Aradu.A01       463100  B       B       A       A       A       A       A       H       B       A       A       H       H       H       H       H       B       A       B       A       H       H       A
Aradu.A01       1089311 A       H       H       H       H       A       A       A       H       A       H       B       A       H       H       H       H       H       A       A       H       H       H

Где ] aradu - ваш пример файла.

Правка, разбивка регулярного выражения:
^ Aradu \. [A-Z] [0-9] {2} = Строки, начинающиеся с "Aradu", за которыми следует литерал "." за которым следует любой символ верхнего регистра, за которым следует любое целое число два раза.
. * A. * B = За ним следует любой символ, любое количество раз (.* ), за которым следует литерал «A», за которым следует литерал «B»
| = логическое или.
(То же начало выражения до)
. * B. * A = Любой символ, повторяющийся любое количество раз, за ​​которым следует литерал 'B', за которым следует буквальный "А".

grep не имеет оператора && (логического и), это самый близкий (насколько мне известно) вы можете найти строку с помощью A && B | | B&&A .

0
28.01.2020, 02:34

У вашего скрипта есть несколько проблем:

  • Он проверяет, соответствует ли какое-либо поле одновременно "A"и "B". Пока поля состоят только из одного символа (поэтому вы не можете получить "AB", "BAA" и т.д.), это никогда не будет правдой.
  • Он ищет H, когда не имеет значения, появляется ли H или нет
  • Он ищет H в $1 (первое поле), каждый раз в цикле
  • Результат всех этих тестов не имеет никакого значения: тест if не имеет никакого действия. Тест print достигается всегда, для каждой строки.

Чтобы отследить, присутствуют ли A и B в одной строке (в разных полях), можно использовать переменную для каждой:

NR>1  {
    #beginning of line - no As or Bs seen yet
    A=0
    B=0
    #looping over all fields except the first two
    #break as soon as both A and B found
    for(i=3; A*B == 0 && i<=NF; i++) {
        if ( $i ~ "A" ) A=1
        if ( $i ~ "B" ) B=1
   }
    #print line if A and B were found
    if (A && B) print
}
2
28.01.2020, 02:34

Теги

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