답변:
이것은 작동 bash하고 zsh리눅스와 OS X에서 테스트 :
sed 's/regexp/\'$'\n/g'
일반적으로 $작은 따옴표로 묶인 문자열 리터럴 bash은 C 스타일 백 슬래시 대체를 수행합니다 (예 : $'\t'리터럴 탭으로 변환). 또한 sed는 개행 문자를 백 슬래시로 이스케이프 처리하기를 원하므로 \이전 $. 마지막으로 달러 기호 자체는 셸에서 해석되도록 따옴표로 묶지 않아야하므로 따옴표 앞에 따옴표 $를 닫았다가 다시여십시오.
편집 : @ mklement0의 의견에서 제안했듯이 다음과 같이 작동합니다.
sed $'s/regexp/\\\n/g'
여기서 일어나는 일은 : 전체 sed 명령은 이제 C 스타일 문자열입니다. 이는 새 줄 리터럴이 다른 백 슬래시로 이스케이프되기 전에 sed가 배치되어야하는 백 슬래시를 의미합니다. 더 읽기 쉽지만이 경우 셸 문자열 대체를 수행 할 수 없습니다 (다시 작성하지 않아도 됨).
sed '\(first match\)\(second match\)/\1\'$'\n''\2/g'입니다. \ n 뒤에 두 개의 작은 따옴표가 있습니다. 첫 번째 $줄은 " "섹션을 닫아서 나머지 줄이 영향을받지 않도록합니다. 인용 부호가 없으면 \ 2는 무시되었습니다.
sed $'s/regexp/\\\n/g'가독성을 향상 - 유일한주의해야 할 점은 당신이 다음 필요가있다 두배로 모든 리터럴 \ 문자를.
다른 답변 중 일부가 내 버전의 sed에서 작동하지 않았습니다. 의 위치를 전환 &하고하는 \n일을했다.
sed 's/regexp/\n&/g'
편집 : 설치하지 않으면 OS X에서 작동하지 않는 것 같습니다 gnu-sed.
brew install gnu-sed다음gsed 's/regexp/\n&/g'
echo 'alias sed=gsed' >> ~/.bashrc
sed에서는 출력 스트림에 개행을 쉽게 추가 할 수 없습니다. 어색한 연속 줄을 사용해야하지만 다음과 같이 작동합니다.
$ sed 's/regexp/\
&/'
예:
$ echo foo | sed 's/.*/\
&/'
foo
자세한 내용은 여기 를 참조 하십시오 . 조금 덜 어색한 것을 원한다면 perl -pesed 대신 match 그룹을 사용해보십시오 .
$ echo foo | perl -pe 's/(.*)/\n$1/'
foo
$1 그룹이 괄호 안에있는 정규식에서 첫 번째 일치 그룹을 나타냅니다.
perl -pi -e 's/(.*)/\n$1/' foo
내 Mac에서 다음은 줄 바꿈 대신 단일 'n'을 삽입합니다.
sed 's/regexp/\n&/g'
이것은 개행으로 대체됩니다.
sed "s/regexp/\\`echo -e '\n\r'`/g"
sed -i '' -e ...하고 ^M캐럿 M (Ctrl + m)이 파일에 기록되는 데 문제가있었습니다 . 나는 같은 매개 변수로 펄을 사용했다.
\n) 만 사용 합니다.
echo...그리고 개행 없이 잘 작동하더라도 ) vim에서 방금 수행했습니다.
sed "s/regexp/`echo`/g"
`echo`가 발생합니다 빈 문자열 명령 대체는 예외없이 모든 후행 뉴 라인 트림 때문에. 명령 대체를 사용하여 단일 개행을 직접 삽입 할 수있는 방법이 없습니다 ( \n\r추가 CR을 삽입 하는 것은 끔찍한 생각입니다).
이 경우에는 sed를 사용하지 않습니다. 나는 tr을 사용한다.
cat Somefile |tr ',' '\012'
쉼표를 사용하여 캐리지 리턴으로 바꿉니다.
cat Somefile | tr ',' '\n'YMMV
완전한 펄 정규 표현식 지원 (sed로 얻는 것보다 훨씬 강력 함) 의 장점으로 sed에서와 마찬가지로 perl one-liner를 사용할 수 있습니다 . * nix 플랫폼 간에는 변형이 거의 없습니다. perl은 일반적으로 perl입니다. 따라서 특정 시스템의 sed 버전을 원하는 방식으로 수행하는 방법에 대해 걱정하지 않아도됩니다.
이 경우에는 할 수 있습니다
perl -pe 's/(regex)/\n$1/'
-pe sed의 정상 작동 모드와 매우 유사하게 펄을 "실행 및 인쇄"루프에 넣습니다.
' 쉘이 방해하지 않도록 다른 모든 것을 인용
()정규 표현식을 둘러싼 그룹화 연산자입니다. $1대치의 오른쪽에이 parens에 일치하는 것이 인쇄됩니다.
마지막으로 \n줄 바꿈입니다.
괄호를 그룹화 연산자로 사용하는지 여부에 관계없이 일치시키려는 괄호를 피해야합니다. 따라서 위에 나열된 패턴과 일치하는 정규식은 다음과 같습니다.
\(\d\d\d\)\d\d\d-\d\d\d\d
\(또는 \)리터럴 패런과 \d일치하고 숫자 와 일치합니다.
보다 나은:
\(\d{3}\)\d{3}-\d{4}
나는 중괄호 안의 숫자가 무엇을하는지 알아낼 수 있다고 생각합니다.
또한 정규 표현식에 / 이외의 구분 기호를 사용할 수 있습니다. 따라서 일치 해야하는 경우 / 탈출 할 필요가 없습니다. 아래 중 하나는 내 대답의 시작 부분에있는 정규식과 같습니다. 이론적으로 당신은 표준 /의 문자 를 대체 할 수 있습니다 .
perl -pe 's#(regex)#\n$1#'
perl -pe 's{(regex)}{\n$1}'
몇 가지 최종 생각.
사용은 -ne대신 -pe유사하게 작용하지만, 자동으로 마지막에 인쇄되지 않습니다. 직접 인쇄하려는 경우 편리 할 수 있습니다. 예를 들어, 여기 grep-alike가 있습니다 ( m/foobar/정규식 일치).
perl -ne 'if (m/foobar/) {print}'
줄 바꿈 문제를 다루는 것을 발견하고 마술처럼 다루기를 원한다면을 추가하십시오 -l. 그러나 개행 작업을 한 OP에게는 유용하지 않습니다.
보너스 팁-pcre 패키지가 설치되어 있으면 pcregrep전체 perl 호환 정규식을 사용 하는이 함께 제공됩니다 .
리눅스에서 출력 스트림에 개행을 삽입하려면 다음을 사용했습니다.
sed -i "s/def/abc\\\ndef/" file1
어디에 file1있었 습니까 ?
def
sed 전체 교체 전, 그리고 :
abc
def
sed 전체 교체 후. 의 사용에 유의하십시오 \\\n. "내부에 패턴이 있으면를 사용하여 이스케이프 처리하십시오 \".
sed삽입 \n합니다 \\n. ---이 코드는 작동합니다 sed -i "s/def/abc\ndef/" file1. --- GNU sed version 4.2.1, GNU bash, version 4.1.2(1) / 4.2.25(1)(CentOS 릴리스 6.4 / Ubuntu 12.04.3).
sed에서는 "\ 1", "\ 2"등으로 패턴의 그룹을 참조 할 수 있습니다. 따라서 찾고있는 패턴이 "PATTERN"이고 그 앞에 "BEFORE"를 삽입하려는 경우 , 당신은 산세 탈출을 사용할 수 있습니다
sed 's/(PATTERN)/BEFORE\1/g'
즉
sed 's/\(PATTERN\)/BEFORE\1/g'
-v패턴을 제공하기 위해 awk를 사용하여이 작업을 수행 할 수도 있습니다 .
awk -v patt="pattern" '$0 ~ patt {gsub(patt, "\n"patt)}1' file
라인에 주어진 패턴이 포함되어 있는지 확인합니다. 그렇다면 시작 부분에 새 줄을 추가합니다.
기본 예를 참조하십시오.
$ cat file
hello
this is some pattern and we are going ahead
bye!
$ awk -v patt="pattern" '$0 ~ patt {gsub(patt, "\n"patt)}1' file
hello
this is some
pattern and we are going ahead
bye!
한 줄의 모든 패턴에 영향을 미칩니다.
$ cat file
this pattern is some pattern and we are going ahead
$ awk -v patt="pattern" '$0 ~ patt {gsub(patt, "\n"patt)}1' d
this
pattern is some
pattern and we are going ahead
1은 Awk에서 축약 형으로 사용됩니다 {print $0}. 그 이유는 True로 평가되는 모든 조건이 현재 레코드 인쇄로 구성된 Awk의 기본 동작을 트리거하기 때문입니다.
이 질문에 대한 모든 답을 읽은 후에도 여전히 다음 예제 스크립트에 올바른 구문을 얻으려고 많은 시도가 필요했습니다.
#!/bin/bash
# script: add_domain
# using fixed values instead of command line parameters $1, $2
# to show typical variable values in this example
ipaddr="127.0.0.1"
domain="example.com"
# no need to escape $ipaddr and $domain values if we use separate quotes.
sudo sed -i '$a \\n'"$ipaddr www.$domain $domain" /etc/hosts
스크립트는 \n단일 sed명령을 사용하여 파일 끝에 줄 바꿈 과 다른 텍스트 줄을 추가합니다 .
sed '/regex/G'