최근 수정된 하위 디렉터리 나열

최근 수정된 하위 디렉터리 나열

그래서 마지막으로 수정된 하위 디렉터리를 얻으려고 합니다.

즉. 1727 8개의 백업이 있지만 최신 백업 디렉터리의 내용만 수집하도록 작성하는 스크립트를 원합니다. 각 백업 실행은 해당 상위 디렉터리 아래에 새로운 하위 디렉터리를 가져옵니다.

[root@localhost backups]# find . -mindepth 2 -maxdepth 2 -not -empty -type d | grep -v logs
./1014/backup_1083219
./1014/backup_1082586
./1014/backup_1081955
./1014/backup_1081334
./1014/backup_1089443
./1014/backup_1080711
./1014/backup_1090690
./1014/backup_1091313
./1014/backup_1090062
./350/backup_1043735
./350/backup_1087678
./350/backup_1088301
./350/backup_1090170
./350/backup_222862
./350/backup_1059530
./350/backup_1088925
./350/backup_1091416
./350/backup_1089549
./350/backup_1090793
./1854/backup_1091300
./460/backup_1089536
./460/backup_1090781
./460/backup_1090159
./460/backup_1086423
./460/backup_1087045

| ls -td -- */를 추가할 수 있다는 것을 알고 있지만 그래도 최신 하위 디렉토리만 포함된 디렉토리 목록을 제공하는 데는 도움이 되지 않습니다.

이상적으로는 다음과 같은 내용을 출력으로 원합니다(하위 폴더가 모두 새로 수정되었다고 가정).

./1727/backup_1059492
./1113/backup_862734
./881/backup_1088974
./1014/backup_1089443
./350/backup_1059530
./1854/backup_1091300
./460/backup_1086423

생각해보면 모든 디렉터리와 하위 디렉터리를 처리하려면 while 루프가 필요할 수도 있겠다는 생각이 들지만 잘 모르겠습니다.

답변1

에서는 zsh다음을 수행할 수 있습니다.

for d (<->(NF)) print -rC1 -- $d/backup_<->(N/om[1])

backup_xxx각 디렉토리 에 대해 yyy최신 1개의 하위 디렉토리.

또는:

for d (<->(NF)) print -rC1 -- $d/backup_<->(N/n[-1])

가장 높은 숫자를 가진 사람에게.

  • <->모든 ASCII 십진수 시퀀스와 일치합니다.
  • (NF), (N/n[-1])... 지정하다글로벌 예선
  • /파일 형식 선택목차
  • FF모든 디렉터리를 선택합니다 (유사 /하지만 빈 디렉터리 제외).
  • nnumericglobsort파일 이름에 일련의 10진수가 포함된 경우 glob에 대한 숫자 정렬을 켭니다.
  • om o수정 시간을 기준으로 정렬합니다 m(예: 최신 항목부터 오래된 항목 순 ls -t).
  • [1]첫 번째, [-1]마지막 것을 선택하세요.
  • print -rC1 -- printr칼럼에 있습니다 1 C.

또 다른 접근 방식은 줄당 최신 것부터 오래된 것 순으로 파일을 나열하고 awk각 최상위 디렉터리의 첫 번째 디렉터리를 사용하여 선택하는 것입니다. 파일 목록을 길들인 이름을 가진 파일로 제한하는 한 괜찮습니다.

print -rC1 -- <->/backup_<->(N/om) | awk -F/ '!seen[$1]++'

(또는 nOn하위 디렉터리 중 om가장 높은 하위 디렉터리 대신).<number>backup_<number>

이전 솔루션과의 차이점은 이전 방법에서 대신 사용한 것처럼 현재 디렉터리의 심볼릭 링크를 따른다는 것입니다 <->(N-F).<->(NF)

GNU를 사용하면 find다음과 같은 방법으로도 수행할 수 있습니다.

LC_ALL=C find . -mindepth 2 -maxdepth 2 -regextype posix-extended \
  -regex './[0-9]+/backup_[0-9]+' -type d -printf '%T@/%P\n' |
  sort -rn |
  awk -F/ '!seen[$2]++ {print $2"/"$3"}'

또는 하위 디렉터리 <number>내 최상위 하위 디렉터리 의 경우 backup_<number>:

LC_ALL=C find . -mindepth 2 -maxdepth 2 -regextype posix-extended \
  -regex './[0-9]+/backup_[0-9]+' -type d -printf '%P\n' |
  sort -t_ -k2rn |
  awk -F/ '!seen[$2]++'

이러한 디렉터리를 목록으로 가져오면 통화에 전달할 수 있습니다 grep. 예를 들면 다음과 같습니다.

(){ dirs=( $^@/backup_<->(N/om[1]) ) } <->(NF)
(( $#dirs )) && grep -re pattern -- $dirs

또는 여기의 디렉토리 이름이 매우 평범하고 특수 문자를 포함하지 않기 때문에 xargs위의 솔루션 중 하나를 선택하고 파이프하십시오 xargs -r grep -re pattern --( -rGNU 확장으로, 둘 다 xargs관련 grep없는 의미를 가짐).

제한되지 않은 디렉토리 이름의 경우 NUL로 구분된 레코드를 사용하고( -N또는 에 옵션 추가 print) 에 옵션을 추가할 수 있습니다.-v ORS='\0'gawk-0xargs


¹ 디렉터리 수정 시간은 디렉터리 내의 파일 데이터가 수정될 때가 아니라 디렉터리에 항목이 추가/제거/이름 변경될 때 업데이트되므로 실제로 원하는 시간이 아닐 수도 있습니다.

관련 정보