백슬래시를 sed로 교체

백슬래시를 sed로 교체

저는 C:\두 가지 다른 유형의 파일을 모두 /root.

내 나무는 다음과 같습니다

- Batch
  - Place of the script
- Conf
  - Appli1
    - File1.xml
    - File2.xml
    - ...
  - Appli2
    - File1.xml
    - File2.xml
    - ...
  - ...
- Info
  - File1.conf
  - File2.conf
  - ...

내 스크립트는 다음과 같습니다 /Batch.

#/bin/bash
find ../ -name "*.xml" -o name "*.conf" -print | xargs sed -i 's C:\ /root/ g'

그러나 오류가 있습니다 sed part.character 14: command 's' unfinished

왜 이런 일이 발생합니까?

답변1

당신은 어디에 사용합니까:

sed -i 's C:\ /root/ g'

당신은 사용하고 있습니다s주문하다명령의 여러 부분을 공백 문자로 구분하는 것은 드물지만 완전히 유효합니다. 그러나 구분 기호 앞에 백슬래시가 있으면 구분 기호로 처리되지 않고 매개 변수 자체의 일부로 처리됩니다.

여기서 문제는 백슬래시가 C:\중간 공백을 벗어나므로 s대체 끝을 찾을 수 없으며(현재로서는 g) 보시다시피 명령이 완료되지 않는다고 불평한다는 것입니다.

최소한 다른 백슬래시를 사용하여 백슬래시 자체를 이스케이프 처리해야 합니다.

sed -i 's C:\\ /root/ g'

공백을 다른 문자로 바꾸는 것이 더 명확할 수도 있지만 이 방법은 작동합니다.


귀하의 용도에 관해서는xargs및 하위 디렉토리 - xargs여기서는 필요하지 않습니다.find하위 디렉터리의 파일 처리를 포함하여 이 작업을 직접 수행할 수 있습니다. 사용:

find ../ \( -name "*.xml" -o -name "*.conf" \) -exec sed -i -e 's|C:\\|/root/|g' '{}' +

find명령 sed자체와 찾은 모든 파일 이름을 실행하십시오 . 대신 파일 이름을 삽입하면 명령 실행 횟수가 최소화 {}됩니다 .+find

-execdir-exec아마도 설명된 일부 보안상의 이유보다 더 나을 것입니다.find매뉴얼 페이지; 비표준 확장이지만 GNU 도구를 사용하는 것 같으니 필요할 경우 있어야 합니다.

답변2

이것은 백슬래시입니다. 백슬래시는 다음 문자를 파괴하고 특별한 의미를 잃습니다. sed 명령은 사용자가 입력한 내용을 읽습니다(여기서는 sed 표현식만 사용하고 지루한 쉘 명령줄 전체를 수행하지는 않습니다).

s
<SPACE>
C
:
Literal <SPACE>
/root/
<SPACE>

찾기 위한 표현식으로 사용하려는 토큰과 그 교체를 sed에게 지시했습니다. 하지만 sed는 다음과 같은 것을 보고 싶어합니다:

s
<SPACE>
C
:
Literal \
<SPACE>
/root/
<SPACE>

백슬래시를 리터럴 백슬래시로 바꾸려면 백슬래시 앞에 백슬래시를 추가하세요.

sed -e 's C:\\ /root '

개인적으로는 공백을 사용하지 않는 것이 좋습니다. 나는 |같은 것을 사용하거나 ;. 그러나 백슬래시에는 여전히 문제가 있습니다. 정말 흥미로운 점은 백슬래시를 구분 기호로 사용하기 위해 입력해야 하는 내용을 알아내는 것입니다. :)

관련 정보