Introducción
Contenido
Verificar si existe un archivo o directorio es una operación simple e importante en muchas tareas. Antes de acceder a un archivo, debemos comprobar si existe para evitar una NullPointerException
. Lo mismo ocurre con los directorios.
Si bien algunas funciones pueden crear un nuevo archivo / directorio si el solicitado no existe, esto puede ser lo contrario de lo que queremos. Si deseamos agregar más información a un archivo existente y el método se ejecuta sin una advertencia, ya que crea el nuevo archivo que necesita, es posible que hayamos perdido algo de información sin darnos cuenta.
Aquí, tenemos una estructura simple:
02/13/2020 11:53 AM <DIR> directory
02/13/2020 11:55 AM <SYMLINKD> directory_link [directory]
02/13/2020 11:53 AM 0 file.txt
02/13/2020 11:55 AM <SYMLINK> symlink.txt [file.txt]
Hay una file.txt
archivo y un symlink.txt
archivo. los symlink.txt
archivo es un enlace simbólico al file.txt
.
Del mismo modo, tenemos un directory
y un enlace simbólico a él – directory_link
.
Compruebe si existe un archivo
Para trabajar con el Files
clase, necesitas estar familiarizado con la Path
clase. Files
solo acepta Path
, y no File
objetos.
Para los propósitos del tutorial, definiremos un File
y Path
instancia para el file.txt
en nuestro directorio:
final static String location = "C:\file.txt";
Path path = Paths.get(location);
File file = new File(location);
Archivos.existe ()
Dicho esto, la primera forma en que podemos verificar si existe un archivo es a través del Files
clase:
// Check if file exists through a Path
System.out.println(Files.exists(path));
// Check if a file exists by converting File object to Path
System.out.println(Files.exists(file.toPath()));
Ejecutar este código nos dará:
true
true
Files.notExists ()
Quizás se pregunte por qué notExists()
el método existe en absoluto:
Si exists()
devoluciones true
, Eso significa que notExists()
debería volver false
. Son plugins lógicos y A = !B
, ¿derecho?
Bueno, ahí es donde muchos se equivocan. Si Files.exists()
devoluciones false
, eso no tiene que significar que el archivo no existe.
También puede significar que la existencia del archivo no se puede verificar. En ese caso, ambos Files.exists()
y Files.notExists()
volvería false
, ya que Java no puede determinar si el archivo existe o no.
Esto suele ocurrir si tiene un archivo que está bloqueado de una manera que Java no puede acceder a él. Imagina que tuviéramos un archivo que está bloqueado en nuestro directorio. lockedFile.txt
:
Y si intentáramos verificar su existencia con:
System.out.println(Files.exists(path));
System.out.println(Files.notExists(path));
Seríamos recibidos con:
false
false
Existe, obviamente, pero Java no tiene permiso para confirmarlo en nuestro sistema, lo que da resultados contradictorios.
Files.isRegularFile ()
Además, podemos comprobar si el archivo es un archivo normal (false
si es un directorio) a través del isRegularFile()
método:
System.out.println(Files.isRegularFile(path));
La salida es:
true
File.isFile ()
En lugar de utilizar el Files
class, también podemos realizar métodos en los propios objetos de archivo:
System.out.println(file.isFile());
Esto devuelve:
true
El archivo existe()
Similar a la opción anterior, podemos ejecutar el exists()
método:
System.out.println(file.exists());
Y esto también vuelve:
true
La diferencia entre estos dos es que el primero verifica si es un archivo y el otro verifica si existe. En diferentes circunstancias, arrojarían resultados diferentes.
Archivos bloqueados
Algo divertido de tener en cuenta es que si está utilizando un File
para verificar la existencia, Java puede determinar si el archivo bloqueado de antes existe o no:
System.out.println(file.isFile());
System.out.println(file.exists());
Ejecutar este fragmento de código producirá:
true
true
Con esto, es evidente que el archivo bloqueado se puede leer utilizando el File
clase en lugar de la Files
clase de ayudante.
Compruebe si existe un directorio
Los directorios son esencialmente archivos que pueden contener otros archivos. Es por eso que comprobar si un directorio es un archivo devolverá true
. Sin embargo, si está comprobando si un directorio es un directorio (un tipo especial de archivo), obtendrá un resultado más preciso.
Esta vez, cambiaremos nuestra ubicación a:
final static String location = "C:\directory";
Archivos.existe ()
Nuevamente, al igual que en el primer ejemplo, podemos verificar si existe a través de:
System.out.println(Files.exists(path));
La salida es:
true
Files.isDirectory ()
Si quisiéramos verificar si es específicamente un directorio, usaríamos:
System.out.println(Files.isDirectory(path));
Y la salida es:
true
Nota: Si el directorio no existe, la isDirectory()
el método regresará false
. Se debe a la forma en que se nombra el método. Lo que hace es: comprueba si el archivo existe y si es un directorio, no solo este último. Un archivo no puede ser un directorio si no existe, por lo tanto, false
es regresado.
Compruebe si el archivo es un enlace simbólico
También puede comprobar si un archivo es solo un enlace simbólico. En ese caso, usaría el Files
clase.
Cambiemos nuestra ubicación a:
final static String location = "C:\symlink.txt";
Files.isSymbolicLink ()
Como de costumbre, el Files
la clase acepta un Path
al archivo:
System.out.println(Files.isSymbolicLink(path));
Ejecutar esto produciría:
true
File.getCanonicalPath () frente a File.getAbsolutePath ()
Otra forma de verificar un enlace simbólico es comparar los resultados de la ruta canónica y la ruta absoluta del archivo. Si son diferentes, lo más probable es que sea un enlace simbólico:
System.out.println(file.getCanonicalPath());
System.out.println(file.getAbsolutePath());
Como estamos buscando un enlace simbólico y sabemos que lo es, estos deberían devolver un resultado diferente: un symlink.txt
y file.txt
camino:
C:symlink.txt
C:symlink.txt
Sin embargo, este no es el caso aquí. Esto se debe al hecho de que el enlace simbólico se creó en Windows con NTFS (New Technology File System). El enlace simbólico se creó utilizando el mklink
comando en el CMD.
Compruebe si existe alguno
De los ejemplos anteriores, es evidente que el Files.exists()
el método regresará true
para archivos y directorios existentes. Sin embargo, no funciona mejor cuando se trata de archivos bloqueados.
Por otro lado, el exists()
método del File
la clase también volverá true
para archivos y directorios y puede leer el archivo bloqueado que el Files
la clase no puede.
Conclusión
Verificar la existencia de archivos y directorios es la primera línea de defensa contra archivos y directorios faltantes. Los diferentes enfoques tienen diferentes contratiempos y puede suponer que un método devolverá un resultado preciso, pero no lo hará debido a cómo funciona en segundo plano.
Ser consciente de qué métodos devuelven qué resultados y qué circunstancias le permitirá evitar desagradables excepciones al manejar archivos.
Después de verificar si su archivo existe o no, es probable que desee leer y escribir archivos en Java.