연습용으로 작성한 스크립트는 다음과 같습니다. 현재 디렉터리 하위 트리에서 모든 일반 파일을 반복적으로 찾고 마지막 수정 날짜를 어제 날짜로 변경해야 합니다.
#!/bin/bash
YESTERDAY=$(date -d yesterday)
RFILES=$(ls -lR | egrep '^-' | rev | cut -d" " -f1 | rev)
for i in $RFILES ; do
ABSPATH=$(readlink -f $i)
touch "$ABSPATH" -d "$YESTERDAY"
done
다음과 같은 하위 트리가 있는 디렉터리에서 호출하면:
a
|___ b
| |__ file1
| |__ file2
|
|__ file3
|__ file4
readlink
예상대로 작동하지 않습니다. 내 말은 그것이 나에게 알려주고 file1
디렉토리 file2
내부에 있다는 것을 의미합니다 a
. 따라서 touch
마지막 수정 날짜를 변경하는 데 사용하면 file1
어제 날짜로 디렉터리에 날짜가 두 개 더 생성됩니다.file2
a
답변1
첫째, 명령은 ls -lR | egrep '^-' | rev | cut -d" " -f1 | rev
경로가 아닌 파일 이름만 표시합니다. 경로가 포함된 모든 파일을 가져와야 하는 경우 find ./ -type f
해당 출력을 사용하고 구문 분석할 수 있습니다. 따라서 readlink -f $i
명령이 필요하지 않습니다.
둘째, 보다 효율적인 솔루션이 필요한 경우 find
인수가 포함된 명령 만 있으면 됩니다 exec
.
find . -type f -exec touch -d "$YESTERDAY" {} +
-type f find regular files
답변2
readlink 프로그램은 기호 링크의 위치를 읽는 데 사용됩니다. 일반 파일만 있는 경우 해당 작업에 더 나은 도구가 있을 수 있습니다. 파일을 찾으려면 find
명령을 사용하는 것을 좋아합니다. find를 사용하면 전체 연습을 한 단계로 수행할 수 있는 것 같습니다.
find . -type f -exec touch {} -d "$(date -d yesterday)" \;
find .
: 현재 디렉토리.
와 그 아래의 모든 항목을 검색합니다.-type f
: 일반 파일만 검색-exec
: find에게 발견된 각 객체에 대해 다음 명령을 실행하도록 지시합니다.touch {} -d "$(date -d yesterday)" \;
: 각 파일에서 실행하려는 명령입니다. "{}"는 출력을 위한 자리 표시자find
이고 \는-exec
문의 끝을 지정합니다.
답변3
RFILES는 경로가 없는 파일 이름일 뿐입니다. readlink
아니요 find
, 사용자가 지정한 이름을 사용하며 경로가 없으면 현재 디렉터리에 있다고 가정합니다.
최신 bash 사용:
shopt -s globstar
RFILES=( ** )
readlink
그러나 출력을 직접 사용할 필요는 없습니다 ls
. 그것은 globstar
간단합니다:
touch -d "$YESTERDAY" $(ls -d **)
실제로는 필요하지도 않습니다 ls
.
touch -d "$YESTERDAY" **
그렇지 않은 경우 find
:
find . -type f -exec touch -d "$YESTERDAY" {} +
마지막으로 날짜 사양은 touch
생각보다 유연합니다.
touch -d yesterday **
작동할 것이다...