Quel est le meilleur moyen de générer un nom de fichier unique et court en Java

Je ne veux pas nécessairement utiliser des UUID car ils sont assez longs.

Le fichier doit simplement être unique dans son répertoire.

Une idée qui vient à l’esprit est d’utiliser File.createTempFile(Ssortingng prefix, Ssortingng suffix) , mais cela semble faux car le fichier n’est pas temporaire.

La casse de deux fichiers créés dans la même milliseconde doit être traitée.

Eh bien, vous pouvez utiliser la version à 3 arguments: File.createTempFile(Ssortingng prefix, Ssortingng suffix, File directory) qui vous permettra de le placer où vous le souhaitez. Sauf si vous le lui dites, Java ne le traitera pas différemment des autres fichiers. Le seul inconvénient est que le nom de fichier doit comporter au moins 8 caractères (minimum de 3 caractères pour le suffixe, plus 5 caractères ou plus générés par la fonction).

Si c’est trop long pour vous, je suppose que vous pouvez toujours commencer par le nom de fichier “a” et parcourir “b”, “c”, etc. jusqu’à ce que vous en trouviez un qui n’existe pas déjà.

J’utiliserais la bibliothèque Apache Commons Lang ( http://commons.apache.org/lang ).

Il existe une classe org.apache.commons.lang.RandomSsortingngUtils qui peut être utilisée pour générer des chaînes aléatoires de longueur donnée. Très pratique non seulement pour la génération de noms de fichiers!

Voici l’exemple:

 Ssortingng ext = "dat"; File dir = new File("/home/pregzt"); Ssortingng name = Ssortingng.format("%s.%s", RandomSsortingngUtils.randomAlphanumeric(8), ext); File file = new File(dir, name); 

J’utilise l’horodatage

c’est à dire

 new File( simpleDateFormat.format( new Date() ) ); 

Et avoir le simpleDateFormat initialisé à quelque chose comme:

 new SimpleDateFormat("File-ddMMyy-hhmmss.SSS.txt"); 

MODIFIER

Qu’en est-il de

 new File(Ssortingng.format("%s.%s", sdf.format( new Date() ), random.nextInt(9))); 

Sauf si le nombre de fichiers créés dans la même seconde est trop élevé.

Si c’est le cas et que le nom n’a pas d’importance

  new File( "file."+count++ ); 

: P

Cela fonctionne pour moi:

 Ssortingng generateUniqueFileName() { Ssortingng filename = ""; long millis = System.currentTimeMillis(); Ssortingng datetime = new Date().toGMTSsortingng(); datetime = datetime.replace(" ", ""); datetime = datetime.replace(":", ""); Ssortingng rndchars = RandomSsortingngUtils.randomAlphanumeric(16); filename = rndchars + "_" + datetime + "_" + millis; return filename; } 

// USE:

 Ssortingng newFile; do{ newFile=generateUniqueFileName() + "." + FileExt; } while(new File(basePath+newFile).exists()); 

Les noms de fichiers de sortie doivent ressembler à:

 2OoBwH8OwYGKW2QE_4Sep2013061732GMT_1378275452253.Ext 

Si vous avez access à une firebase database, vous pouvez créer et utiliser une séquence dans le nom du fichier.

 select mySequence.nextval from dual; 

Il sera garanti d’être unique et ne devrait pas être trop volumineux (à moins que vous ne déversiez une tonne de fichiers).

Regardez le fichier javadoc , la méthode createNewFile ne créera le fichier que s’il n’existe pas et renverra un booléen pour indiquer si le fichier a été créé.

Vous pouvez également utiliser la méthode exist ():

 int i = 0; Ssortingng filename = Integer.toSsortingng(i); File f = new File(filename); while (f.exists()) { i++; filename = Integer.toSsortingng(i); f = new File(filename); } f.createNewFile(); System.out.println("File in use: " + f); 

Pourquoi ne pas utiliser quelque chose basé sur un horodatage ..?

En combinant d’autres réponses, pourquoi ne pas utiliser le timestamp ms avec une valeur aléatoire ajoutée; répétez jusqu’à l’absence de conflit, ce qui dans la pratique ne sera presque jamais.

Par exemple: File-ccyymmdd-hhmmss-mmm-rrrrrr.txt

Que diriez-vous de générer sur la base de l’horodatage arrondi à la milliseconde près, ou quelle que soit la précision dont vous avez besoin … puis utilisez un verrou pour synchroniser l’access à la fonction.

Si vous stockez le dernier nom de fichier généré, vous pouvez append des lettres séquentielles ou d’autres chiffres au besoin pour le rendre unique.

Ou si vous préférez le faire sans verrous, utilisez un pas de temps plus un identifiant de thread, et assurez-vous que la fonction dure plus d’une milliseconde, ou attend qu’elle le fasse.

Il semble que vous ayez une poignée de solutions pour créer un nom de fichier unique. Je testerais le nom de fichier de cette façon:

  Ssortingng filePath; boolean fileNotFound = true; while (fileNotFound) { Ssortingng testPath = generateFilename(); try { RandomAccessFile f = new RandomAccessFile( new File(testPath), "r"); } catch (Exception e) { // exception thrown by RandomAccessFile if // testPath doesn't exist (ie: it can't be read) filePath = testPath; fileNotFound = false; } } //now create your file with filePath 

Cela fonctionne aussi

 Ssortingng logFileName = new SimpleDateFormat("yyyyMMddHHmm'.txt'").format(new Date()); logFileName = "loggerFile_" + logFileName; 

Je comprends que je suis trop tard pour répondre à cette question. Mais je pense que je devrais le dire car cela semble différent des autres solutions.

Nous pouvons concaténer threadname et timeStamp actuel en tant que nom de fichier. Mais avec ceci, il y a un problème comme un nom de thread qui contient un caractère spécial comme “\”, ce qui peut créer un problème lors de la création du nom de fichier. Donc, nous pouvons supprimer le nom spécial du nom du thread, puis concaténer le nom du thread et l’horodatage

 fileName = threadName(after removing special charater) + currentTimeStamp 

Pourquoi ne pas utiliser synchronisé pour traiter multi thread. voici ma solution: elle peut générer un nom de fichier court et unique.

 private static synchronized Ssortingng generateFileName(){ Ssortingng name = make(index); index ++; return name; } private static Ssortingng make(int index) { if(index == 0) return ""; return Ssortingng.valueOf(chars[index % chars.length]) + make(index / chars.length); } private static int index = 1; private static char[] chars = {'a','b','c','d','e','f','g', 'h','i','j','k','l','m','n', 'o','p','q','r','s','t', 'u','v','w','x','y','z'}; 

blow est la fonction principale pour le test, c’est le travail.

 public static void main(Ssortingng[] args) { List names = new ArrayList<>(); List threads = new ArrayList<>(); for (int i = 0; i < 100; i++) { Thread thread = new Thread(new Runnable() { @Override public void run() { for (int i = 0; i < 1000; i++) { String name = generateFileName(); names.add(name); } } }); thread.run(); threads.add(thread); } for (int i = 0; i < 10; i++) { try { threads.get(i).join(); } catch (InterruptedException e) { e.printStackTrace(); } } System.out.println(names); System.out.println(names.size()); } 
  //Generating Unique File Name public Ssortingng getFileName() { Ssortingng timeStamp = new SimpleDateFormat("yyyy-MM-dd_HH:mm:ss").format(new Date()); return "PNG_" + timeStamp + "_.png"; }