파일 이름 끝에 수정된 날짜 타임스탬프를 사용하여 여러 파일의 이름을 바꾸시겠습니까?

파일 이름 끝에 수정된 날짜 타임스탬프를 사용하여 여러 파일의 이름을 바꾸시겠습니까?

예를 들어, g.txt가 2012년 6월 20일에 마지막으로 수정된 여러 파일(예: g.txt)을 포함하는 디렉터리가 있습니다.

g.txt와 같은 모든 파일의 이름을 일괄적으로 바꾸고 마지막 수정 날짜인 2012년 6월 20일을 끝에 추가하는 방법은 무엇입니까?

답변1

이것은 goldschrafe의 라인 버전입니다.

  • 통계를 사용하지 않음

  • 이전 버전의 GNU 날짜

  • 파일 이름의 공백을 올바르게 처리하십시오.

  • 대시로 시작하는 파일 이름도 처리합니다.

    for f in *; do mv -- "$f" "$f-$(date -r "$f" +%Y%m%d)"; done


업데이트 2021-03-20

이 질문에 대한 내 답변은 수년 동안 저를 괴롭혔습니다(음, 제가 기억할 때만 - 오늘처럼 다시 찬성표를 얻은 날에만). 그래서 마침내 업데이트하게 되었습니다. 위의 원래 답변은 여전히 ​​​​작동하지만 아래의 업데이트 된 답변이 더 좋습니다.

좋다어느배치 파일 이름 바꾸기 작업의 경우 다음을 사용하여 수행해야 합니다.진주 rename루프에 대해 투박한 쉘을 사용하는 대신 유틸리티입니다.

Perl 이름 바꾸기 유틸리티는 실제로 간단한 s/search/replace/정규식 작업(대부분의 이름 바꾸기 작업에 충분함)부터 복잡한 여러 줄 스크립트에 이르기까지 Perl 코드를 사용하여 파일 이름을 바꿀 수 있는 특수 스크립트 언어입니다.

예를 들어

rename -n 'BEGIN {use Date::Format};
           die $! unless -f $_;
           next if (m/-\d{8}$/);
           my $ts=(stat($_))[9];
           my $dt=time2str("%Y%m%d",$ts);
           s/$/-$dt/;' *.txt

여기에는 Perl과 Date::Format모듈만 필요합니다(이 모듈은 매우 유용하며 Perl이 있는 모든 시스템에 설치해야 합니다. IMO it 및 작성자 Graham Barr의 Date::Parse모듈,~해야 한다Perl 핵심 모듈 라이브러리의 일부이지만 그렇지 않으므로 설치하려면 cpan배포 패키지(예: Debian 패키지)를 사용해야 합니다.libtimedate-perl

그런데 이 스크립트는 파일 이름 끝에 이미 날짜(예: 8자리)가 있는 것처럼 보이는 모든 파일을 건너뜁니다.

또는 파일 접미사(있는 경우) 앞에 날짜를 추가하는 고급 버전의 경우:

rename -n 'BEGIN {use Date::Format; use File::Basename};
           die $! unless -f $_;
           my ($filename,$dirs,$suffix) = fileparse($_,qr/\.[^.]*/);
           next if (m/-\d{8}${suffix}$/);
           my $ts=(stat($_))[9];
           my $dt=time2str("%Y%m%d",$ts);
           s/${suffix}$/-${dt}${suffix}/;' *.txt

File::Basename이 모듈은 내가 기억하는 한(적어도 10년, 아마도 그 이상) Perl의 표준 핵심 모듈로 포함되었기 때문에 이 버전에 대한 추가 요구 사항은 없습니다 .

노트:위의 두 스크립트 모두 결과를 적용하기 전에 테스트/시뮬레이션할 수 있도록 rename이름 바꾸기 -n(일명 ) "dry-run" 옵션을 사용합니다. --nono요구 사항을 충족한다고 확신하면 제거하세요 -n(또는 자세한 출력으로 바꾸세요).-v

또한 참고하십시오:다른 Perl rename스크립트와 마찬가지로 명령줄 및/또는 표준 입력에서 제공하는 파일 이름을 바꿀 수 있습니다. 예를 들어 현재 디렉터리와 모든 하위 디렉터리에 있는 모든 .txt 파일의 이름을 바꾸려면 다음을 수행하세요.

find . -type f -iname '*.txt' -print0 | 
   rename -0 --nofullpath -n '..........'

그런데 여기서는 rename--nofullpath(일명 -d, --filenmame, --nopath) 옵션을 사용하여 찾은 파일 경로의 파일 이름 부분만 이름을 바꾸도록 합니다. 이 특별한 경우에는 필요하지 않습니다(예제 이름 바꾸기 스크립트는 파일 이름의 끝만 변경하기 때문). 그러나 경로와 파일 이름의 이름을 바꾸지 않으려는 경우에는 일반적으로 좋은 생각입니다(예: 's/ //g'파일 이름에서 공백을 제거하는 이름 바꾸기 스크립트는 경로에 있는 모든 공백과 선행하지 않는 파일 이름을 제거하려고 하면 --nofullpath오류로 인해 실패할 수 있습니다.

마침내:Perl 이름 바꾸기 스크립트( Fedora 및 RedHat에서 File::Rename때때로 호출되는 , 또는 )를 이름 바꾸기라는 다른 프로그램과 혼동하지 마십시오. prenameperl-rename오직이 Perl 기반 이름 바꾸기 유틸리티는 위에 표시된 대로 임의의 Perl 코드를 사용하여 파일 이름을 바꿀 수 있습니다. 다른 이름 바꾸기 유틸리티에는 다른 기능과 다르고 호환되지 않는 명령줄 옵션이 있습니다.

올바른 이름 바꾸기가 설치되었는지 확인할 수 있습니다.

$ rename -V
/usr/bin/rename using File::Rename version 1.13, File::Rename::Options version 1.10

prename실행 파일은 또는 시스템에서 호출될 수 있으므로 perl-rename해당 실행 파일을 사용해 보고 위의 예를 조정하여 올바른 실행 파일 이름을 사용하십시오.file-rename-V

답변2

현재 디렉토리에 있는 모든 (와일드카드) 파일의 이름 을 바꾸는 빠르고 더러운 Bash 한 줄 filename.txt:filename.txt-20120620

for f in *; do mv -- "$f" "$f-$(stat -c %Y "$f" | date +%Y%m%d)"; done

나는 진취적인 Bash 괴짜가 그것을 깨뜨릴 수 있는 특별한 사례를 찾을 것이라고 확신합니다. :)

분명히 이것은 파일 끝에 날짜처럼 보이는 것이 이미 있는지 확인하는 것과 같은 원하는 효과를 얻지 못합니다.

답변3

필수 zsh 단일 라이너(선택적 구성 요소의 일회성 로드 제외):

zmodload zsh/stat
autoload -U zmv
zmv -n '(*)' '$1-$(stat -F %Y%m%d +mtime -- $1)'

우리는 stat내장을 사용합니다zsh/stat기준 치수,게다가zmv파일 이름을 바꾸는 기능. 연장 날짜 앞에 날짜를 추가하는 추가 항목입니다(있는 경우).

zmv -n '(*)' '$1:r-$(stat -F %Y%m%d +mtime -- $1)${${1:e}:+.$1:e}'

답변4

이것은 (goldschrafe의 oneliner 기반) 확장된 cas의 oneliner 버전입니다.멱등성,

즉, 날짜/시간 접두사가 있는 파일로 확장되고아직 날짜/시간 접두사가 없는 사용자에게만 이 작업을 수행하세요..

사용 사례: 디렉터리에 새 파일을 추가하고 아직 날짜/시간 접두사가 추가되지 않은 파일에 날짜/시간 접두사를 추가하려는 경우 유용합니다.

for f in * ; do
  if [[ "$f" != ????-??-??' '??:??:??' - '* ]]; then
    mv -v -- "$f" "$(date -r "$f" +%Y-%m-%d' '%H:%M:%S) - $f" ;
  fi;
done

관련 정보