Как удалить дубликаты символов?

18

Если у меня есть строка как:

Thhiisss iisss mmyyy nameeee

Я хочу напечатать это как:

This is my name

Что такое команда Unix для этого?

Кришна
источник
Можете ли вы предоставить больше информации о происхождении дубликатов и желаемом результате? Что делать, если «Mmyyy nameee iisss Jesssssiiieee»?
Пауло Алмейда

Ответы:

24

С tr:

echo "Thhiisss iisss mmyyy nameeee" | tr -s 'a-z'

Пояснение: -sПереключатель tr«сжимает» повторяющиеся символы. Как показано, переключатель может использоваться с рядом символов: aдо z.

MKC
источник
2
Некоторое объяснение команды может быть полезным для будущих читателей.
Компьютерщик
8

В системе GNU вам нужно использовать sedили подобное, если ваша локаль использует многобайтовые символы ( как предлагает jimmij ), потому что GNU trможет ссылаться только на символ на байт. В локали ASCII вы можете удалить все дубликаты, trнапример:

LC_ALL=C tr -s '\0-\255' <input

Так...

echo Thhiisss iisss mmyyy nameeee|
LC_ALL=C tr -s '\0-\255'

... печать ...

This is my name

Вы также можете сделать это выборочно, ссылаясь на ваши цели по диапазону:

echo TThhiisss iisss mmyyy nameeee|
LC_ALL=C tr -s '\101-\132'

...или...

echo TTTThhiisss iisss mmyyy nameeee|
LC_ALL=C tr -s '[:upper:]'

... которые работают как одно и то же, и которые оба печатают:

Thhiisss iisss mmyyy nameeee

... или использование [:punct:], [:digit:], [:lower:], [:alpha:]или все , что вы хотели бы. Вы также можете отменить выбор с / -cтак ...

echo 'TTTThhiisss     iisss mmyyy nameeee' |
LC_ALL=C tr -cs '[:upper:]'

... печать ...

TTTThis is my name
mikeserv
источник
7

Один из способов с sed:

sed ':X;s/\(.\)\1/\1/g;tX'

или даже проще:

sed 's/\(.\)\1*/\1/g'

(спасибо Костас и Микесерв за комментарии).

jimmij
источник
sed 's/\(.\)\1\+/\1/g'
Костас
3

Попробуй tr:

echo "Thhiisss iisss mmyyy nameeee" | tr -s 'hismye'
heemayl
источник