sed의 패턴과 일치하지 않는 문자열의 모든 문자를 바꾸는 방법은 무엇입니까?

sed의 패턴과 일치하지 않는 문자열의 모든 문자를 바꾸는 방법은 무엇입니까?

"something_something_something"과 같은 문자열이 있습니다.

이제 문자열은 다음 패턴을 가져야 합니다.^[a-zA-Z0-9](-*[a-zA-Z0-9])*

패턴과 일치하지 않는 문자열의 모든 문자를 바꾸는 방법은 무엇입니까?

내 예를 들어, 나는 다음을 수행해야 합니다:

somethingsomethingsomething

나는 그것을 시도했지만 sed -n '/^[a-zA-Z0-9](-*[a-zA-Z0-9])*/p'성공하지 못했습니다.

답변1

첫째, sed -E패턴이 확장 정규식(ERE)으로 해석되고 일반 괄호가 그룹화에 사용되도록 해야 합니다. 기본적으로 sed의 패턴은 BRE(Basic Regular Expressions)이며 \(및 를 사용해야 합니다 \).

둘째, sed -n '/.../p'작동하지만 부분적으로 일치하는 경우 전체 줄을 인쇄합니다. 패턴도 마지막에 고정된 경우 전체 행을 삭제하는 것이 유용합니다.

패턴에 맞지 않는 부분을 제거하려면 다음과 같이 하세요.

sed -E -e 's/^([a-zA-Z0-9](-*[a-zA-Z0-9])*).*/\1/' input.txt

후행은 .*전체 줄이 일치하는지 확인한 다음 모든 것이 첫 번째 캡처 그룹의 내용으로 대체됩니다. input 의 경우 패턴의 주요 부분과 일치하지 않는 것으로 something_something_something인쇄됩니다 .something_

귀하의 패턴은 와 동일해 보입니다 [-a-zA-Z0-9]+. 아마도 비슷한 것을 의미하는 것 같습니다 [a-zA-Z0-9]+(-[a-zA-Z0-9]+)*. 이는 foo또는 같은 문자열 과 일치해야 합니다 foo-bar-doodoo(그러나 그렇지 않음 foo--bar).

답변2

sNr(search n replacement)라는 쉘 변수에 저장된 또 다른 정규식을 작성하고 여기에 인용된 정규식 중 일부를 추가합니다.

확실하지 않은 문자는 해시 값(#)으로 대체됩니다.

sNr='
 s@
  \(
   \(
    \(
      [a-zA-Z0-9](-*[a-zA-Z0-9])*
    \)\{1,\}
    #*
  \)*
 \)
 [^a-zA-Z0-9#]
 @\1#@
';

echo something_something_something |
sed -e "
  :loop
    ${sNr//[$IFS]/}
  tloop
"
something#something#something

관련 정보