После того, как задал вопрос об ubuntuforums.org и не получил удовлетворительного ответа, я решил снова задать вопрос здесь, на Ask Ubuntu. Мне нужно, чтобы ответ был очень подробным. В частности, мне нужно знать, какие строки сравниваются каждый раз, когда строка печатается с использованием uniq для следующих двух примеров:
file1.txt:
$ cat -A file1.txt
aaa^Iupc$
b$
c$
aaa^Iztp$
b$
c$
C$
A$
B$
B$
b$
$ sort file1.txt | uniq -f 1
A
aaa upc
aaa ztp
b
и file2.txt:
$ cat -A file2.txt
aaa^Iupc$
b$
c$
aaa^Iztp$
b$
c$
C$
A$
B$
B$
bbb^Ixpz$
$ sort file2.txt | uniq -f 1
A
aaa upc
aaa ztp
b
bbb xpz
c
Я запутался во втором примере. Я не понимаю, как в верхнем регистре B не заканчивается окончательный вывод. Должна ли печататься строка с верхним регистром В, если строки B и bbb xpz находятся рядом друг с другом? Если:
B ---> (empty)
и
bbb ---> xpz
пустое значение и xpz являются уникальными, поэтому обе строки должны быть напечатаны. Или я что-то упускаю?
Ответ заключается в порядке сортировки и в том, что uniq использует для значения поля, когда меньше, чем заданный номер поля (N) существует при использовании -f N.
Как вы видели имеют кодировки ASCII, поэтому порядок сортировки очень предсказуем:
% sort file.txt
A
aaa upc
aaa ztp
b
b
B
B
bbb xpz
c
c
C
Теперь давайте используем uniq -f 1 для получения уникальных строк с пропуском первого поля каждой отдельной строки при проверке:
% sort file.txt | uniq -f 1
A
aaa upc
aaa ztp
b
bbb xpz
c
Теперь важно отметить, что uniq использует пустую строку для строк, которая имеет меньше упомянутых полей, 1 в этом случае; поэтому все строки, которые имеют только одно поле, будут рассматриваться как имеющие нулевые строки для других полей, в то время как по сравнению с другими строками, имеющими> = 2 поля.
Итак, из выхода sort file2.txt:
b
b
B
B
все будут рассматриваться как одни и те же, и сохранится только первая строка, содержащая b, поэтому у вас есть b на выходе.
Точно так же из:
c
c
C
только выход c попадет в выход uniq.
Вот таблица, которая может помочь вам в этом:
----------------+---------------+----------+----------------+
sort | Remove | Adjacent | |
(C locale) | field #1 | match? | Output |
----------------+---------------+----------+----------------+
A | | N* |A |
B | | Y | |
B | | Y | |
C | | Y | |
aaa upc | upc | N |aaa upc |
aaa ztp | ztp | N |aaa ztp |
b | | N |b |
b | | Y | |
bbb xpz | xpz | N |bbb xpz |
c | | N |c |
c | | Y | |
----------------+---------------+----------+----------------+
* the first line has no adjacent above, so is always output
Ответ заключается в порядке сортировки и в том, что uniq использует для значения поля, когда меньше, чем заданный номер поля (N) существует при использовании -f N.
Как вы видели имеют кодировки ASCII, поэтому порядок сортировки очень предсказуем:
% sort file.txt
A
aaa upc
aaa ztp
b
b
B
B
bbb xpz
c
c
C
Теперь давайте используем uniq -f 1 для получения уникальных строк с пропуском первого поля каждой отдельной строки при проверке:
% sort file.txt | uniq -f 1
A
aaa upc
aaa ztp
b
bbb xpz
c
Теперь важно отметить, что uniq использует пустую строку для строк, которая имеет меньше упомянутых полей, 1 в этом случае; поэтому все строки, которые имеют только одно поле, будут рассматриваться как имеющие нулевые строки для других полей, в то время как по сравнению с другими строками, имеющими> = 2 поля.
Итак, из выхода sort file2.txt:
b
b
B
B
все будут рассматриваться как одни и те же, и сохранится только первая строка, содержащая b, поэтому у вас есть b на выходе.
Точно так же из:
c
c
C
только выход c попадет в выход uniq.
Вот таблица, которая может помочь вам в этом:
----------------+---------------+----------+----------------+
sort | Remove | Adjacent | |
(C locale) | field #1 | match? | Output |
----------------+---------------+----------+----------------+
A | | N* |A |
B | | Y | |
B | | Y | |
C | | Y | |
aaa upc | upc | N |aaa upc |
aaa ztp | ztp | N |aaa ztp |
b | | N |b |
b | | Y | |
bbb xpz | xpz | N |bbb xpz |
c | | N |c |
c | | Y | |
----------------+---------------+----------+----------------+
* the first line has no adjacent above, so is always output