(원래 위치가 아닌) 위치와 일치하는 폴더의 파일에 대해 반복적으로 명령을 실행합니다.

(원래 위치가 아닌) 위치와 일치하는 폴더의 파일에 대해 반복적으로 명령을 실행합니다.

폴더의 파일을 폴더 내의 파일 .docx로 재귀적으로 변환하고 싶습니다 . .doc문제는 모든 출력 파일이 소스 파일 위치가 아닌 다음 명령을 실행하는 폴더에 생성된다는 것입니다.

find -type f -name "*.docx"-exec libreoffice --convert-to doc {} \;

libreofficefind 는 명령에 소스 파일을 제공하고 출력은 분명히 현재 위치에 있어야 한다는 것을 알고 있습니다 . 그렇다면 명령을 사용하여 폴더를 반복적으로 반복하고 파일이 발견된 위치에서 명령을 실행하려면 어떻게 해야 합니까? 초기보다는?

답변1

-execdir당신이 그것을 지원한다면 그것이 목적입니다 find. Linux 시스템의 기본 GNU에는 find이 기능이 있습니다. 에서 man find:

-execdir 명령;

-execdir 명령{} +

-exec와 비슷하지만 지정된 명령은 일반적으로 검색을 시작한 디렉터리가 아닌 일치하는 파일이 포함된 하위 디렉터리에서 실행됩니다. [. . . ]

그래서 당신은 다음을 원합니다:

find . -type f -name "*.docx" -execdir libreoffice --convert-to doc {} \;

파일 이름은 각 인스턴스에 삽입됩니다 {}. -exec사용하는 경우 {}로 시작하는 상대 경로가 포함됩니다 ./. -execdir사용하는 경우 {}파일 이름만 사용합니다.

답변2

이를 수행하려면 find 출력을 쉘 명령에 전달할 수 있어야 합니다.

find . -type f -name \*.docx -exec sh -c 'echo libreoffice --convert-to-doc {} --outdir $(dirname {})' \;

댓글에서 @EdgarMagallon의 제안은 실제로 내 것보다 간단합니다. 물론, 이 사용 사례에서는 그의 명령을 추천합니다.

답변3

문제는 -execdir다음을 교체 하여 해결됩니다.-exec

find . -type f -name "*.docx" -execdir libreoffice --convert-to doc {} \;

답변4

--output-dir문서가 있는 디렉토리를 사용 하거나 해당 디렉토리로 변경하십시오. 아래에서는 비표준(그러나 일반적으로 구현되는) -execdir조건 자를 사용하지 않고 이를 수행하는 방법을 보여 드리겠습니다 find.

이는 발견된 파일의 경로 이름을 해당 파일을 반복하는 짧은 인라인 스크립트에 전달합니다. 발견된 각 이름에 대해 스크립트는 파일이 발견된 디렉터리로 변경되고 그곳에서 변환을 수행합니다. 이는 cd서브셸에서 수행되므로 나머지 스크립트 환경은 영향을 받지 않습니다.

find . -name '*.docx' -type f -exec sh -c '
    for pathname do
        ( cd "$(dirname "$pathname")" && libreoffice --convert-to doc "$(basename "$pathname")" )
    done' sh {} +

다음은 유사하지만 작업 디렉터리를 변경하지 않습니다. 대신 --outdir옵션을 사용하여 변환된 문서가 기록될 디렉터리 경로를 지정합니다.

find . -name '*.docx' -type f -exec sh -c '
    for pathname do
        libreoffice \
            --convert-to doc "$pathname" \
            --outdir "$(dirname "$pathname")"
    done' sh {} +

위의 쉘 코드에서는 (remove the shortest suffix string match ) "$(dirname "$pathname")"로 대체할 수 있고 , (remove the longest prefix string match ) 로 대체할 수 있다 ."${pathname%/*}""$pathname"/*"$(basename "$pathname")""${pathname##*/}""$pathname"*/

관련 정보