sed на Linux: замена строк, правка in-place и регулярки
sed (stream editor) — стандартная команда Linux для построчной обработки текста: замена, удаление, печать строк по шаблону. Работает с потоком (pipe) или файлами, поддерживает in-place редактирование. Базовый инструмент шелл-скриптов после `grep` и `awk`.
sed: потоковый редактор для шелла и скриптов
sed (stream editor) — стандартная команда Linux для построчной обработки текста: замена, удаление, печать строк по шаблону. Работает с потоком (pipe) или файлами, поддерживает in-place редактирование. Базовый инструмент шелл-скриптов после grep и awk.
Что такое sed
sed читает входной поток (stdin или файл) построчно, для каждой строки выполняет указанный сценарий (одну или несколько команд) и выводит результат. Состояние между строками не сохраняется — это и есть «потоковость».
echo "hello world" | sed 's/world/Linux/'
# hello Linux
sed создан в 1970-х для систем без полноценных редакторов; стандартизирован POSIX. На Ubuntu по умолчанию идёт GNU sed — у него больше расширений по сравнению с BSD-вариантом (на macOS).
Базовый синтаксис
sed [опции] '<скрипт>' [файл...]
Скрипт — одна или несколько команд через ; или через -e. Самые частые команды:
s/PATTERN/REPLACEMENT/— замена.d— удалить строку.p— напечатать строку (используется с-nдля подавления авто-печати).y/abc/xyz/— транслитерация (какtr).q— выйти.
Опции:
-n— не печатать строки автоматически (только то, что явно черезp).-i— править файл in-place.-Eили-r— extended regex (поддержка+,?,(),|без экранирования).-e <script>— добавить команду; можно несколько-e.
Замена строк через s///
Самая частая операция:
echo "hello world" | sed 's/world/Linux/'
# hello Linux
# Все вхождения в строке
echo "one two one" | sed 's/one/ONE/g'
# ONE two ONE
# Только второе вхождение
echo "one two one one" | sed 's/one/ONE/2'
# one two ONE one
Флаги после s///:
g— global, все вхождения в строке (по умолчанию — только первое).i— case-insensitive.N(число) — заменить только N-е вхождение.
Разделитель не обязан быть / — особенно полезно для путей:
echo "/home/user/file" | sed 's|/home/user|/var/data|'
# /var/data/file
Можно использовать :, |, # или любой другой символ. sed возьмёт первый символ после s как разделитель.
Правка файла in-place
Самая популярная задача — изменить файл на месте:
sed -i 's/PasswordAuthentication yes/PasswordAuthentication no/' /etc/ssh/sshd_config
-i (--in-place) переписывает файл. Опасно: если регулярка не совпадёт, файл останется как есть; если совпадёт неправильно, изменения уже применены.
Безопасный паттерн — сделать бэкап:
sed -i.bak 's/old/new/g' config.ini
# создаст config.ini.bak с оригиналом
.bak — суффикс для копии. Можно -i'.orig', -i.20260504 и т. д.
Перед -i всегда тестируйте без него:
sed 's/old/new/g' config.ini # покажет результат, не изменит файл
Если результат правильный — добавляйте -i.
Удаление строк
# Удалить строки с "DEBUG"
sed '/DEBUG/d' app.log
# Удалить пустые строки
sed '/^$/d' file.txt
# Удалить комментарии (строки начинающиеся с #)
sed '/^#/d' /etc/ssh/sshd_config
# Удалить первую строку
sed '1d' file.txt
# Удалить с 5-й по 10-ю строку
sed '5,10d' file.txt
# Удалить с 100-й до конца
sed '100,$d' file.txt
Адрес перед командой — это диапазон, в котором её применять. Самые полезные:
N— номер строки./PATTERN/— строки, совпадающие с regex.N,M— диапазон номеров./PAT1/,/PAT2/— между двумя шаблонами.$— последняя строка.
Печать строк (-n + p)
С флагом -n sed не печатает строки автоматически — выводится только то, что явно через p:
# Эмуляция grep
sed -n '/error/p' app.log
# Печать с 10-й по 20-ю строку
sed -n '10,20p' file.txt
# Печать строк между двумя маркерами
sed -n '/^### START/,/^### END/p' notes.md
# Печать с именем файла (как grep -H)
for f in *.conf; do sed -n "s/^/$f: /; /pattern/p" "$f"; done
Это часто проще, чем head | tail, особенно когда нужно вырезать диапазон.
Регулярки в sed
GNU sed по умолчанию использует basic regex (BRE):
.— любой символ.*— 0+ повторений.^/$— начало / конец строки.[abc]/[^abc]— символьный класс.\(...\)/\{N,M\}— группы и кванторы (со экранированием).
С -E (или -r) включается extended regex (ERE) — те же +, ?, (), | без экранирования:
# Basic — нужно экранировать (
sed 's/\(foo\)\(bar\)/\2\1/' file.txt
# Extended — без экранирования
sed -E 's/(foo)(bar)/\2\1/' file.txt
\1, \2 — обратные ссылки на группы. & в replacement — все совпадение целиком:
# Обернуть числа в скобки
echo "Версия 24.04 LTS" | sed -E 's/[0-9]+\.[0-9]+/(&)/'
# Версия (24).04 LTS
# С `+` в ERE — целое число
echo "Версия 24.04 LTS" | sed -E 's/[0-9]+\.[0-9]+/(&)/'
# Версия (24.04) LTS
Несколько команд
Через ; или -e:
# Удалить пустые и комментарии
sed -E '/^$/d; /^#/d' /etc/sshd_config
# Через -e
sed -e 's/foo/FOO/g' -e 's/bar/BAR/g' file.txt
# Скрипт из файла
sed -f script.sed input.txt
Боевые сценарии
1. Подмена в конфиге.
sudo sed -i 's/^#PasswordAuthentication yes$/PasswordAuthentication no/' /etc/ssh/sshd_config
sudo sshd -t
sudo systemctl restart ssh
^...$ — якоря: совпадает только полная строка. Без них s/yes/no/ заменит первое yes где попало.
2. Замена IP в большом конфиге.
sudo sed -i 's/192\.168\.1\.50/192.168.10.50/g' /etc/nginx/sites-available/*
sudo nginx -t
sudo systemctl reload nginx
\. — экранированная точка (в regex . означает любой символ).
3. Чистка пустых и закомментированных строк.
sed -E '/^[[:space:]]*$/d; /^[[:space:]]*#/d' /etc/myapp/config.ini
[[:space:]]* учитывает табуляции и пробелы перед #.
4. Извлечение значения из конфига.
# Достать значение Port из sshd_config
sed -n 's/^Port[[:space:]]*\([0-9]*\)$/\1/p' /etc/ssh/sshd_config
-n + p — печатать только захваченное; \1 — первая группа.
5. Замена в нескольких файлах сразу.
find /etc/myapp -name "*.conf" -exec sed -i 's|/old/path|/new/path|g' {} +
Через find + -exec. Подробнее — глоссарий find.
6. Конвертация CRLF в LF (Windows-line-endings → Linux).
sed -i 's/\r$//' file.txt
Альтернативно — утилита dos2unix.
7. Добавление строки после совпадения.
sed -i '/^server {/a\ listen 80;' nginx.conf
Команда a\ — append, добавить строку после совпадения. i\ — insert, перед.
Грабли sed
-iбез бэкапа. Один неверный regex — и конфиг переписан. Привычка: сначала без-i, проверить, потом с-i.bak.- Разделитель в путях.
s/\/home\/user\/file/.../— нечитаемо. Используйтеs|/home/user/file|...|. .в regex. Точка означает любой символ, не литеральную точку. В IP-адресах и именах файлов экранируйте:\.или[.].- macOS sed отличается от GNU. На macOS
-iтребует обязательный аргумент (даже пустой-i ''). На Ubuntu/Linux работает и-iсам по себе. Если скрипт нужен кроссплатформенно — пишите-i.bakи удаляйте бэкапы потом. - GNU-расширения.
-E,\u,\l,\U,\L(изменение регистра) есть только в GNU sed. Для портабельности — POSIX-минимум. - Перевод строки в replacement. Чтобы вставить
\nв замене:sed 's/, /\n/g'(в GNU sed). В POSIX — через настоящий перевод строки в одинарных кавычках.
sed vs awk
Обе утилиты обрабатывают текст построчно, но решают разные задачи:
- sed — простые замены и удаления одной командой. Когда нужно «заменить X на Y» — sed.
- awk — обработка по столбцам, агрегаты, условия, переменные. Когда нужно «для каждой строки сделать что-то сложное с полями» — awk.
# sed — заменить
sed 's/error/ERROR/g' app.log
# awk — посчитать колонки
awk '{ sum += $3 } END { print sum }' data.txt
В реальности часто комбинируют через пайпы: grep | sed | awk | sort | uniq -c.
Альтернативы sed
perl -pe— perl как sed-on-steroids. Поддержка PCRE, мощнее замены.ripgrep --replace— современный rg может не только искать, но и заменять.sd— современная замена sed на Rust с человеческим CLI:sd 'old' 'new' file.txt.
В скриптах автоматизации остаётся sed — он стандартен и есть на любой UNIX-системе.
Частые вопросы
Что такое sed в Linux
Stream Editor — потоковый редактор. Читает текст построчно, применяет команды к каждой строке (замена, удаление, печать), выводит результат. Работает с pipe или файлами; поддерживает регулярные выражения. Стандартный инструмент шелл-скриптов начиная с UNIX 1970-х.
Чем sed отличается от awk
sed фокусируется на построчных трансформациях через простые команды (s, d, p). awk работает со столбцами, поддерживает переменные, условия, функции — это полноценный мини-язык. Для замены и удаления берите sed; для парсинга колонок и агрегатов — awk.
Как заменить текст в файле через sed
sed -i 's/old/new/g' file.txt. Флаг -i правит файл на месте, s — substitute, g — global (все вхождения в строке). Перед -i всегда тестируйте без него: sed 's/old/new/g' file.txt покажет результат, не меняя файл.
Как использовать sed с регулярками
По умолчанию sed работает с basic regex (нужно экранировать (, ), +, ?). С флагом -E (или -r) включается extended regex — те же (, +, ?, | без экранирования. Захват групп — \(...\) в BRE или (...) в ERE; обратные ссылки в replacement — \1, \2.
Как удалить пустые строки через sed
sed '/^$/d' file.txt. ^$ — пустая строка (начало и конец без содержимого). Для удаления строк только из пробелов: sed '/^[[:space:]]*$/d'. С -i правит файл на месте.
Как сделать sed безопасным
- Перед
-iвсегда тестируйте без него — посмотрите вывод. 2) Используйте-i.bakдля бэкапа. 3) Якорите regex (^pattern$), чтобы не зацепить лишнее. 4) Экранируйте точки в IP и путях:\.. 5) Для путей выбирайте альтернативный разделитель:s|...|...|.
Что значит s/old/new/g в sed
Команда замены. s — substitute, old — что искать (regex), new — на что заменить, g — флаг global (все вхождения в строке). Без g заменится только первое вхождение в каждой строке. Разделители (/) можно поменять на | или другой символ для удобства.
Что запомнить
- Замена:
sed 's/PATTERN/REPLACEMENT/g'. С-i— на месте, без-i— в stdout. - Удаление:
sed '/PATTERN/d'. Якоря^и$— для точных совпадений. - Перед
-iвсегда тестируйте без него. С-i.bak— бэкап рядом. - В replacement:
&— всё совпадение,\1,\2— группы. - Для путей используйте альтернативные разделители:
s|/home/...|/var/...|вместоs/\/home/.../.... - На macOS
-iнужен аргумент (-i ''), на Ubuntu — нет. Пишите-i.bak, чтобы работало везде. - Для сложной обработки колонок — берите awk или скрипт на Python; sed для простых замен.
Обложка: фото mk. s с Unsplash, лицензия Unsplash.