web-dev-qa-db-ja.com

フォルダ内のファイルの名前を連番に変更する

ディレクトリ内のファイルの名前を連番に変更したい。ファイルの作成日に基づきます。

sadf.jpgから0001.jpgwrjr3.jpgから0002.jpgなどの場合、ファイルの合計量に応じた先行ゼロの数(不要な場合は追加のゼロは不要)。

194
Gnutt

パディングにループ、let、およびprintfを使用してみます。

a=1
for i in *.jpg; do
  new=$(printf "%04d.jpg" "$a") #04 pad to length of 4
  mv -i -- "$i" "$new"
  let a=a+1
done

-iフラグを使用すると、既存のファイルが自動的に上書きされるのを防ぎます。

271
gauteh

一行の美しさ:

ls -v | cat -n | while read n f; do mv -n "$f" "$n.ext"; done 

.ext.pngなどで.jpgを変更できます。

198
user4434168

その単純さのためにgautehのソリューションが好きですが、それには重大な欠点があります。何千ものファイルを実行しているときは、 "引数リストが長すぎます"というメッセージ( more more )が表示されます。次に、スクリプトが非常に遅くなる可能性があります。私の場合は、約36000ファイルでそれを実行し、スクリプトは約移動しました。毎秒1アイテム!なぜこれが起こるのかよくわかりませんが、同僚から得たルールは "findはあなたの友達です"です。

find -name '*.jpg' | # find jpegs
gawk 'BEGIN{ a=1 }{ printf "mv %s %04d.jpg\n", $0, a++ }' | # build mv command
bash # run that command

アイテムを数えてコマンドをビルドするために、 gawk が使われました。ただし、主な違いに注意してください。デフォルトではfindはカレントディレクトリとそのサブディレクトリのファイルを検索するので、必要ならばカレントディレクトリだけで検索を制限することを忘れないでください(方法を見るにはman findを使用してください)。

60
Pero

oSXでPeroのソリューションを使用するには、いくつかの修正が必要でした。私は使った:

find . -name '*.jpg' \
| awk 'BEGIN{ a=0 }{ printf "mv \"%s\" %04d.jpg\n", $0, a++ }' \
| bash

注:バックスラッシュは行継続のためにあります

2015年7月20日編集スペースを含むファイル名をサポートするために、mvコマンドの\"%s\"引数を引用するために@ klaustopherのフィードバックを組み込みました。

28
beibei2

"rename"コマンドで

rename -N 0001 -X 's/.*/$N/' *.jpg

または

rename -N 0001 's/.*/$N.jpg/' *.jpg
25

オリジナルの拡張子を保持し、先行ゼロを追加し、さらにOSXで動作する非常に単純なbash oneライナー。

num=0; for i in *; do mv "$i" "$(printf '%04d' $num).${i#*.}"; ((num++)); done

簡易版 http://ubuntuforums.org/showthread.php?t=1355021

23
Roy Shilkrot

すべての状況で機能するように、名前にスペースを含むファイルには\ "を付けてください。

find . -name '*.jpg' | gawk 'BEGIN{ a=1 }{ printf "mv \"%s\" %04d.jpg\n", $0, a++ }' | bash
11

rename-Nをサポートしていない場合は、次のようにすることができます。

ls -1 -c | xargs rename -n 's/.*/our $i; sprintf("%04d.jpg", $i++)/e'

編集与えられた数字から始めるには、以下の(やや見苦しい)コードを使用することができます。123を希望の数字に置き換えてください。

ls -1 -c | xargs rename -n 's/.*/our $i; if(!$i) { $i=123; } sprintf("%04d.jpg", $i++)/e'

これは作成時間順にファイルをリストし(最も新しいものから、逆ソートのためにlsに-rを追加します)、次に名前を変更するためにこのファイルのリストを送ります。名前の変更は、正規表現でPerlコードを使用してカウンタをフォーマットおよびインクリメントします。

ただし、EXIF情報を含むJPEG画像を扱う場合は、exiftoolをお勧めします。

これは「名前の変更例」の下の exiftoolドキュメント からのものです。

   exiftool '-FileName<CreateDate' -d %Y%m%d_%H%M%S%%-c.%%e dir

   Rename all images in "dir" according to the "CreateDate" date and time, adding a copy number with leading '-' if the file already exists ("%-c"), and
   preserving the original file extension (%e).  Note the extra '%' necessary to escape the filename codes (%c and %e) in the date format string.
8
Luke H

OSXの場合、Homebrewから名前変更スクリプトをインストールします。

brew install rename

それからあなたは本当にばかげて簡単にそれをすることができます:

rename -e 's/.*/$N.jpg/' *.jpg

または、Niceプレフィックスを追加するには

rename -e 's/.*/photo-$N.jpg/' *.jpg
6
trisweb

lsも使えます

ls *.JPG| awk 'BEGIN{ a=0 }{ printf "mv %s gopro_%04d.jpg\n", $0, a++ }' | bash
1
bartburkhardt

findは、項目がディレクトリエントリ内に格納されている順序でディレクトリツリーをトラバースするため、やはり少し変更を加えてPeroのソリューションを使用します。これは、同じマシン上で実行するたびに一貫して実行され、削除が行われていない場合は基本的に「ファイル/ディレクトリの作成順序」になります。

ただし、場合によっては、この例で使用されている名前などの論理的な順序を取得する必要があります。

find -name '*.jpg' | sort -n | # find jpegs
gawk 'BEGIN{ a=1 }{ printf "mv %s %04d.jpg\n", $0, a++ }' | # build mv command
bash # run that command 
1

これらのファイルがディレクトリ内にあり、作成順にリストされているとします。最初のファイルが最も古いファイルです。

a.jpg
b.JPG
c.jpeg
d.tar.gz
e

それからls -1crはまさに上記のリストを出力します。 renameを使うことができます。

ls -1cr | xargs rename -n 's/^[^\.]*(\..*)?$/our $i; sprintf("%03d$1", $i++)/e'

どの出力

rename(a.jpg, 000.jpg)
rename(b.JPG, 001.JPG)
rename(c.jpeg, 002.jpeg)
rename(d.tar.gz, 003.tar.gz)
Use of uninitialized value $1 in concatenation (.) or string at (eval 4) line 1.
rename(e, 004)

拡張子のないファイルには「初期化されていない値の使用[…]」という警告が表示されます。あなたはそれを無視することができます。

実際に名前の変更を適用するには、renameコマンドから-nを削除します。

この答えは Lukeの2014年4月の答え からヒントを得たものです。ファイルの総数に応じて先頭の0の数を設定するというGnuttの要件を無視します

1
Michael Schmid

私は同様の問題を抱えており、そのためにシェルスクリプトを書きました。私はそれが誰かに役立つことができると思うので私はそれが多くの良い答えがすでに掲示されていたにもかかわらずそれを掲示することにしました。それを改善すること自由に感じなさい!

分子

@Gnutt希望する動作は、次のように入力することで実現できます。

./numerate.sh -d <path to directory> -o modtime -L 4 -b <startnumber> -r

オプション-rが省略された場合、リーマはシミュレートされるだけです(テストに役立つはずです)。

オプションL -p <prefix>-s <suffix>で接頭辞/接尾辞を追加することも可能です。

ファイルに番号を付ける前にファイルを番号順にソートしたい場合は、-o modtimeオプションを削除してください。

1
Paul Weibert
ls -1tr | rename -vn 's/.*/our $i;if(!$i){$i=1;} sprintf("%04d.jpg", $i++)/e'

-vnの名前を変更 - 削除nオフテストモード

{$ i = 1;} - 制御開始番号

"%04d.jpg" - コントロールカウントゼロ4そして出力拡張子を設定。jpg

1
maXp
a=1

for i in *.jpg; do
 mv -- "$i" "$a.jpg"
 a=`expr $a + 1`
done
1
Shubh

私には、この答えの組み合わせは完璧に機能しました。

ls -v | gawk 'BEGIN{ a=1 }{ printf "mv %s %04d.jpg\n", $0, a++ }' | bash
  • ls -vは1 10 9を正しい順序で並べるのに役立ちます:1 9 10順序、jpg JPG jpegでのファイル名拡張子問題を回避する
  • gawk 'BEGIN{ a=1 }{ printf "mv %s %04d.jpg\n", $0, a++ }'は4文字と先行ゼロで再番号付けされます。 mvを避けることによって、偶然同じ番号を持つことによってすでにそこにあるものを上書きしようとはしません。
  • bashが実行されます

@xhienneが言ったことに注意してください。未知のコンテンツをbashにパイプすることはセキュリティ上のリスクです。しかし、スキャンした写真を使用していたので、これは当てはまりませんでした。

1
nintendojet

すべてのファイルの名前をsequenceに変更し、拡張子を小文字にします。

rename --counter-format 000001 --lower-case --keep-extension --expr='$_ = "$N" if @EXT' *
0
OzzyCzech

このonelinerは現在のディレクトリ内のすべてのファイルを一覧表示し、作成タイムスタンプによって逆の順序でソートし(最も古いファイルが先頭にあることを意味します)、ファイル数に応じて末尾のゼロで自動的に名前を変更します。ファイル拡張子は保持されます。

私は通常、携帯電話の写真や映画を保存するためのフォルダを1年だけ使用しています。このコマンドを適用すると、テレビやアーカイブで正しい順序でスライドショーをする準備が整います。

ファイル名が競合していると、ファイルが失われることに注意してください。そのため、最初にtemp001.jpgのような変な名前に変更してから、最後のファイル名に実行します。

DIGITS=$(ls | wc -l | xargs | wc -c | xargs); ls -tcr | cat -n | while read n f; do mv "$f" "$(printf "%0${DIGITS}d" $n).${f##*.}"; done
0
Flavio Aiello

時間順にソートされていて、jpg、先行ゼロとベースネームに限定されています(あなたがそうしたいと思う場合):

ls -t *.jpg | cat -n |                                           \
while read n f; do mv "$f" "$(printf thumb_%04d.jpg $n)"; done

\を除いた、すべて一行で)

0
Frank Nocke

他のソリューションの大部分は、すでに番号として名前が付けられている既存のファイルを上書きします。これは、スクリプトを実行し、ファイルを追加してから再度スクリプトを実行する場合に特に問題になります。

このスクリプトは、最初に既存の数値ファイルの名前を変更します。

#!/usr/bin/Perl

use strict;
use warnings;

use File::Temp qw/tempfile/;

my $dir = $ARGV[0]
    or die "Please specify directory as first argument";

opendir(my $dh, $dir) or die "can't opendir $dir: $!";

# First rename any files that are already numeric
while (my @files = grep { /^[0-9]+(\..*)?$/ } readdir($dh))
{
    for my $old (@files) {
        my $ext = $old =~ /(\.[^.]+)$/ ? $1 : '';
        my ($fh, $new) = tempfile(DIR => $dir, SUFFIX => $ext);
        close $fh;
        rename "$dir/$old", $new;
    }
}

rewinddir $dh;
my $i;
while (my $file = readdir($dh))
{
    next if $file =~ /\A\.\.?\z/;
    my $ext = $file =~ /(\.[^.]+)$/ ? $1 : '';
    rename "$dir/$file", sprintf("%s/%04d%s", $dir, ++$i, $ext); 
}
0
Andy Beverley

画像のラベル付けに画像アノテーターを使用している場合。

$ make qt5py3

$ python3 labelImg.py