정규식 \/\*(.|\n)*?\*\/을 사용하여 각 C 여러 줄 주석을 선택했지만 SED에서는 작동하지 않습니다.

정규식 \/\*(.|\n)*?\*\/을 사용하여 각 C 여러 줄 주석을 선택했지만 SED에서는 작동하지 않습니다.

예를 들어 C 스타일의 여러 줄 주석을 일치시켜야 합니다.

#include <stdio.h>

int main()
{
    // this is a dummy function
    float sum = 0;
    // testing the sed commands
    
    int x = 6; // single-line comment
    x = x + 5;
    
    char y = 'n'; /* end of c  *
    file */
}

여러 줄 주석을 모두 제거해야 합니다.

그래서 사용해봤는데 sed s/\/\*\(.\|\n\)*\?\*\///안되네요. : /으로 바꾸려고 시도했지만 여전히 작동하지 않습니다.%s%\/\*\(.\|\n\)*\?\*\/%%

누구든지 이 정규식 \/\*(.|\n)*?\*\/작업을 지시하는 데 도움을 줄 수 있습니까 sed?

답변1

Sed는 \n후행 개행( ) 문자로 정의된 "레코드"(줄)를 처리합니다. 이는 과거 a를 일치시킬 수 없다는 것을 의미합니다. \n왜냐하면 그것에 관한 한 sedthe는 \n레코드의 끝이기 때문입니다. GNU에서는 slurp 파일을 사용하고 전체 파일을 단일 레코드로 처리하여 이 문제를 해결할 sed수 있습니다 ( 파일에 NULL( )이 없으면 파일당 하나의 레코드가 정의됩니다).-z\0\0

$ sed -zE 's|/\*.*\n.*\*/||' file.c 
#include <stdio.h>

int main()
{
    // this is a dummy function
    float sum = 0;
    // testing the sed commands
    
    int x = 6; // single-line comment
    x = x + 5;
    
    char y = 'n'; 
}

그러나 동일한 파일에 여러 줄 주석이 있는 경우 sed탐욕스럽지 않은 일치를 만들 수 없기 때문에 실패하므로 항상 찾기를 시도합니다.가장 긴가능한 일치, 즉 /*처음부터 마지막까지 일치 함을 의미합니다 */. 따라서 다음과 같이 탐욕적이지 않은 일치를 수행할 수 있는 도구를 사용하십시오 perl.

$ perl -0777 -pe 's|/\*.*?\n.*?\*/||gs' file.c 
#include <stdio.h>

int main()
{
    // this is a dummy function
    float sum = 0;
    // testing the sed commands
    
    int x = 6; // single-line comment
    x = x + 5;
    
    char y = 'n'; 
}

그러나 주석이 한 줄만 있으면 /* */실패합니다 . 내가 생각할 수 있는 가장 안전한 방법은 이 작업을 수행하기 위해 정규 표현식을 사용하는 것을 잊어버리고 대신 열린 주석 태그와 닫힌 주석 태그의 수를 기록하고 그에 따라 제거하는 작은 스크립트를 작성하는 것입니다.

/*또 다른 문제는 or이 있는 문자열 */도 이를 깨뜨릴 수 있다는 것입니다. 예를 들어 다음과 같은 것이 있다면 어떨까요?

char foo [ ] = "A comment starts with /*";

결국 유일한 안전한 방법은이 답변통과에드 모튼C 전처리기를 사용합니다.

이것이 C 파일에 있는 경우 다른 도구와 함께 C 전처리기를 사용하여 #define 또는 #include 확장과 같은 특정 전처리기 기능을 일시적으로 비활성화해야 하며, 다른 모든 방법은 극단적인 경우에 실패합니다. 이는 모든 경우에 작동합니다.

[ $# -eq 2 ] && arg="$1" || arg=""
eval file="\$$#"
sed 's/a/aA/g; s/__/aB/g; s/#/aC/g' "$file" |
          gcc -P -E $arg - |
          sed 's/aC/#/g; s/aB/__/g; s/aA/a/g'

이를 쉘 스크립트에 넣고 구문 분석할 파일 이름으로 호출합니다. 선택적으로 적용할 C 표준을 지정하기 위해 "-ansi"와 같은 플래그를 앞에 붙입니다.

바라보다https://stackoverflow.com/a/35708616/1745001더 알아보기.

관련 정보