Перетворення вмісту файлів у малі регістри


85

У мене є tempфайл з невеликим і великим змістом.

Вхідні дані

Зміст мого tempфайлу:

hi
Jigar
GANDHI
jiga

Я хочу перетворити все верхнє на нижнє .

Командування

Я спробував таку команду:

sed -e "s/[A-Z]/[a-z]/g" temp

але отримали неправильний вихід.

Вихідні дані

Я хочу це:

hi
jigar
gandhi
jiga

Що повинно бути в замінній частині аргументу sed?


Відповіді:


122

Якщо ваш вхід містить лише символи ASCII, ви можете використовувати tr:

tr A-Z a-z < input 

або (менш легко запам’ятовувати та вводити IMO; але не обмежуючись лише латинськими літерами ASCII, хоча в деяких реалізаціях, включаючи GNU tr, все ще обмежено однобайтовими символами, тому в локалях UTF-8, все ще обмежених літерами ASCII):

tr '[:upper:]' '[:lower:]' < input

якщо вам доведеться скористатися sed:

sed 's/.*/\L&/g' < input

(тут передбачається реалізація GNU).

За допомогою POSIX sedвам потрібно буде вказати всі транслітерації, а потім ви можете вибрати, які літери ви хочете конвертувати:

sed 'y/AǼBCΓDEFGH.../aǽbcγdefgh.../' < input

З awk:

awk '{print tolower($0)}' < input

3
Зверніть увагу, що \Lце розширення GNU.
— Антон

\Lпрацює добре для мене поки що.
— Освітліть

2
@JigarGandhi. sedє командою Unix. Різні системи мають різні варіанти з різною поведінкою та функціональністю. На щастя, сьогодні існує стандарт, який найбільше відповідає, щоб ви могли розраховувати на мінімальний набір функцій, загальний для всіх. \Lне входить до їх числа і був введений GNU sed(відповідає тому ж оператору в стандарті ex/ vi) і зазвичай не доступний в інших реалізаціях.
— Стефан Шазелас

9
Зауважте, що деякі trреалізації, такі як GNU tr, не працюють належним чином у багатобайтових локалях (більшість з них є сьогодні, спробуйте, echo STÉPHANE | tr '[:upper:]' '[:lower:]'наприклад). У системах GNU ви можете віддати перевагу sedваріанту або awks tolower().
— Стефан Шазелас

5
Незначна корекція: sed 's/.*/\L&/g' < input. \1Посилання на збігається подстроку не працюватиме , якщо не вказана подстрока з дужкою , як wurtle робить в своєму. Однак це трохи чистіше використовувати &для представлення всього матчу, як показано
— Едвард Браун

30

Використовувати vim, це дуже просто:

$ vim filename
gg0guGZZ

Відкриває файл, ggпереходить до першого рядка 0, першого стовпця. З guG, опускає регістр усіх символів до нижньої частини файлу. ZZекономить і виходить.

Він повинен обробляти майже все, що ви на нього кинете; він буде ігнорувати числа, він буде працювати з не ASCII.

Якщо ви хочете зробити навпаки, перетворити літери в нижньому регістрі у верхній регістр, поміняти uна деякі U: gg0gUGZZі ви встановлені.


14
Лол "супер простий"
— blambert

це, очевидно, не підходить для багатьох файлів
— Corey Goldberg

моя найулюбленіша відповідь поки що !!!!
— Мона Джалал

1
@CoreyGoldberg, vim file1 file2 fileetcа потім щось подібне :bufdo gg0guG:w<CR>, ймовірно, буде працювати для будь-якої кількості файлів. Ще не тестували цього!
— TankorSmash

@TankorSmash, який все ще не масштабує велику кількість файлів
— Corey Goldberg,

17

Мені це подобається dd, я сам.

<<\IN LC_ALL=C 2<>/dev/null \
dd conv=lcase
hi
Jigar 
GANDHI
jiga
IN

... стає ...

hi
jigar
ghandi
jiga

LC_ALL=CЄ захист будь-якого мультибайтних на вході - хоч якісь - багатобайтові капіталом не будуть перетворені. Те саме стосується (GNU) tr - обидва додатки схильні до введення маніпуляцій у будь-якій не-C мові. iconvможе поєднуватися з будь-яким для комплексного рішення.

2>/dev/nullRedirect Відкидає ddзвіт За замовчуванням статус - і його STDERR. Без цього ddслід було б виконати таке завдання, як наведена вище інформація про друк, наприклад, скільки байтів було оброблено тощо.


Це рішення набагато швидше, ніж trпри обробці великих файлів, дякую!
— WhiteWinterWolf

13

Ви також можете використовувати Perl 5:

perl -pe '$_=lc' temp

Параметр -pвказує perl виконувати вказаний вираз один раз для кожного рядка введення, друкуючи результат, тобто кінцеве значення $_. -eвказує, що наступним аргументом буде програма, на відміну від файлу, що містить сценарій. lcперетворюється в малі регістри. Без аргументу він буде працювати далі $_. І $_=економить це знову, щоб воно було надруковано.

Варіант цього був би

perl -ne 'print lc' temp

Використання -n- це -pхіба те, що $_в кінцевому підсумку не буде надруковано. Тож замість того, щоб зберігати цю змінну, я включаю явний оператор друку.

Однією з переваг Perl на відміну від sed є те, що вам не потрібні розширення GNU. Є проекти, які повинні бути сумісні з середовищами, що не належать до GNU, але також вже мають залежність від Perl asa. У порівнянні з tr, можливо, Perl lcможе бути легше зрозуміти місцевість. Детальні відомості див. На perllocaleсторінці чоловіка.


9

Вам потрібно зафіксувати узгоджену схему, а потім використовувати її для заміни модифікатором:

sed 's/\([A-Z]\)/\L\1/g' temp

\(...\)«Захоплює» вшита Знайдений текст, то перший захоплення йде до \1, наступний \2і т.д. Нумерація згідно відкривають дужок в разі вкладених захопленнями.

\LЗвернена захоплений візерунок в нижньому регістрі, є також \Uдля верхнього корпусу.


3
вам цього не потрібно - весь малюнок завжди потрапляє&
— mikeserv

Щоправда, але тоді я б упустив можливість пояснити захоплення матчів :-)
— wurtel

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.