📄 java10.htm
字号:
<HTML>
<HEAD>
<TITLE>Java desde Cero</TITLE>
</HEAD>
<BODY background=/iconos/1.gif TEXT=000000 LINK=FF0000 VLINK=A62A2A>
<H1>Un paréntesis de Entrada/Salida<BR>
</H1>
<P>
En Java hay muchas clases para leer y escribir archivos (u otros
dispositivos de E/S). Están reunidos en la biblioteca <B>java.io</B>.
<P>
Vamos a empezar como siempre con un pequeño ejemplo funcional
y en seguida nos meteremos en el necesario camino de las excepciones...
<BR>
<H2>Primera Lectura<BR>
</H2>
<PRE>
<FONT SIZE=2>// archivo: Ejemplo9.java - compilar con "javac Ejemplo9.java", etc. etc.
import java.io.*;
public class Ejemplo9 {
public static void main(String args[]) throws FileNotFoundException,IOException {
FileInputStream fptr;
DataInputStream f;
String linea = null;
fptr = new FileInputStream("Ejemplo9.java");
f = new DataInputStream(fptr);
do {
linea = f.readLine();
if (linea!=null) System.out.println(linea);
} while (linea != null);
fptr.close();
}
}<BR>
</FONT>
</PRE>
<P>
(Caramba! ¿Qué hace ese <I>throws</I> ahí?)
<P>
El programa de ejemplo simplemente lee un archivo de texto y lo
muestra en pantalla, algo así como el <FONT FACE="Arial">type</FONT>
del DOS o el <FONT FACE="Arial">cat</FONT> de Unix.
<P>
Dejemos por ahora el <FONT FACE="Arial">throws FileNotFoundException,IOException</FONT>
y vamos al código.<BR>
<PRE>
<FONT SIZE=2>fptr = new FileInputStream("Ejemplo9.java");
<BR>
</FONT>
</PRE>
<P>
La clase <FONT FACE="Arial">FileInputStream</FONT> (descendiente
de InputStream) nos sirve para referirnos a archivos o conexiones
(sockets) de una máquina. Podemos accederlos pasando un
String como aquí, un objeto de tipo File o uno de tipo
FileDescriptor, pero en esencia es lo mismo. Al crear un objeto
de este tipo estamos "abriendo" un archivo, clásicamente
hablando.
<P>
Si el archivo no existe (por ejemplo reemplacen "Ejemplo9.java"
por alguna otra cosa, como "noexiste.txt"), al ejecutarlo
nos aparece un error:
<PRE>
<FONT SIZE=2>C:\java\curso>java Ejemplo9
java.io.FileNotFoundException: noexiste.txt
at java.io.FileInputStream.<init>(FileInputStream.java:51)
at Ejemplo9.main(Ejemplo9.java:9)<BR>
</FONT>
</PRE>
<P>
(Caramba! ¿Dónde vi ese FileNotFoudException antes?)
<P>
Justamente, cuando el archivo al que quiero acceder no existe,
Java "lanza" una <I>excepción</I>. Esto es, un
aviso de que algo falló y, si no se toma ninguna acción,
detiene el programa.
<P>
La clase <FONT FACE="Arial">FileInputStream</FONT> puede "lanzar"
(throws) la excepción <FONT FACE="Arial">FileNotFoundException</FONT>.
<P>
¿Cómo capturar y tratar las excepciones? En seguida;
primero terminemos con nuestro programa.<BR>
<PRE>
<FONT SIZE=2>f = new DataInputStream(fptr);<BR>
</FONT>
</PRE>
<P>
La clase <FONT FACE="Arial">DataInputStream</FONT> nos permite
leer, en forma independiente del hardware, tipos de datos de una
"corriente" (stream) que, en este caso, es un archivo.
Es descendiente de <FONT FACE="Arial">FilterInputStream</FONT>
e <I>implementa</I> <FONT FACE="Arial">DataInput</FONT>, una <I>interface</I>.
<P>
Al crear un objeto de tipo <FONT FACE="Arial">DataInputStream</FONT>
lo referimos al archivo, que le pasamos como parámetro
(fptr); esta clase tiene toda una serie de métodos para
leer datos en distintos formatos.
<P>
En nuestro programa usamos uno para leer líneas, que devuelve
<I>null</I> cuando se llega al final del archivo o un <FONT FACE="Arial">String</FONT>
con el contenido de la línea:<BR>
<PRE>
<FONT SIZE=2>do {
<B> linea = f.readLine();
</B> System.out.println(linea);
} while (linea != null);<BR>
</FONT>
</PRE>
<P>
En seguida de leer la línea la imprimimos, y repetimos
esto mientras no nos devuelva <FONT FACE="Arial">null</FONT>.
<P>
Al final, cerramos el archivo:<BR>
<PRE>
<FONT SIZE=2>fptr.close();<BR>
</FONT>
</PRE>
<P>
Tanto <FONT FACE="Arial">readLine</FONT> como <FONT FACE="Arial">close</FONT>
pueden lanzar la excepción <FONT FACE="Arial">IOException</FONT>,
en caso de error de lectura o cierre de archivo.
<P>
En realidad, podríamos no haber usado un DataInputStream
y trabajar en forma más directa:<BR>
<PRE>
<FONT SIZE=2>import java.io.*;
public class Ejemplo10 {
public static void main(String args[]) throws FileNotFoundException,IOException {
FileInputStream fptr;
int n;
fptr = new FileInputStream("Ejemplo9.java");
do {
n = fptr.read();
if (n!=-1) System.out.print((char)n);
} while (n!=-1);
fptr.close();
}
}<BR>
</FONT>
</PRE>
<P>
Ya que la clase <FONT FACE="Arial">FileInputStream</FONT> también
dispone de métodos para leer el archivo. Sólo que
son unos pocos métodos que nos permiten leer un entero
por vez o un arreglo de bytes. <FONT FACE="Arial">DataInputStream</FONT>
tiene métodos para leer los datos de muchas formas distintas,
y en general resulta más cómodo.<BR>
<H2>Capturando excepciones</H2>
<P>
Ahora sí, vamos a ver cómo nos las arreglamos con
las excepciones para que no se nos pare el programa con un mensaje
tan poco estético...
<P>
En lugar de lanzar las excepciones al intérprete, vamos
a procesarlas nosotros mediante la cláusula <FONT FACE="Arial">catch</FONT>:
<BR>
<PRE>
<FONT SIZE=2> // Archivo: Ejemplo11.java
// Compilar con: javac Ejemplo11.java
<B> // Ejecutar con: java Ejemplo11 <nombre_archivo>
</B>import java.io.*;
public class Ejemplo11 {
<B>public static void main(String args[]) {
</B>FileInputStream fptr;
DataInputStream f;
String linea = null;
<B>try {
fptr = new FileInputStream(args[0]);
</B>f = new DataInputStream(fptr);
do {
linea = f.readLine();
if (linea!=null) System.out.println(linea);
} while (linea != null);
fptr.close();
}
<B>catch (FileNotFoundException e) {
System.out.println("Hey, ese archivo no existe!\n");
}
catch (IOException e) {
System.out.println("Error de E/S!\n");
}
</B>}
}<BR>
</FONT>
</PRE>
<P>
También hicimos un cambio para elegir el archivo a imprimir
desde la línea de comandos, en lugar de entrarlo fijo,
utilizando para eso el argumento del método <FONT FACE="Arial">main(arg[])</FONT>,
que consiste en una lista de <I>Strings</I> con los parámetros
que se pasan en la línea a continuación de <FONT FACE="Arial">java
nombre_programa</FONT>. Por ejemplo, si llamamos a este programa
con:
<PRE>
<FONT SIZE=2> java Ejemplo11 archi.txt otro.xxx<BR>
</FONT>
</PRE>
<P>
<FONT FACE="Arial">arg[0]</FONT> contendrá "archi.txt",
<FONT FACE="Arial">arg[1]</FONT> contendrá "otro.xxx",
y así sucesivamente.
<P>
Por supuesto, si llamamos a <FONT FACE="Arial">Ejemplo11</FONT>
sin parámetros se lanzará otra excepción
al intentar accederlo:
<PRE>
<FONT SIZE=2>C:\java\curso>java Ejemplo11
java.lang.ArrayIndexOutOfBoundsException: 0
at Ejemplo11.main(Ejemplo11.java:10)<BR>
</FONT>
</PRE>
<P>
Pero también podríamos capturarla!
<P>
Veamos un poquito cómo es esto de capturar excepciones.
<P>
La cláusula <B><FONT FACE="Arial">try</FONT></B> engloba
una parte del programa donde se pueden lanzar excepciones. Si
una excepción se produce, Java busca una instrucción
<B><FONT FACE="Arial">catch</FONT></B> <B><FONT FACE="Arial">(nombre_de_la_excepción
variable)</FONT></B>, y, si la encuentra, ejecuta lo que ésta
engloba. Si no encuentra un <FONT FACE="Arial">catch</FONT> para
esa excepción, para el programa y muestra el error que
se produjo.
<P>
Por ejemplo, para evitar este último error bastaría
con agregar:<BR>
<PRE>
<FONT SIZE=2>catch (ArrayIndexOutOfBoundsException e) {
System.out.println("Debe ingresar un nombre de archivo!");
System.out.println("Ej.: java Ejemplo11 pepe.txt");
}<BR>
</FONT>
</PRE>
<P>
Hay que notar que cuando se lanza una excepción el programa
igual se detiene, porque el código que sigue al lanzamiento
de la excepción no se ejecuta. Veremos luego cómo
se comporta esto en un objeto que fue creado por otro, y cómo
usar la instrucción <FONT FACE="Arial">finally</FONT> para
poner una parte de código que se ejecute pase lo que pase.
<BR>
<H2>Los applets y los archivos</H2>
<P>
Veamos cómo se comporta esta aplicación si la modificamos
para usarla como applet.<BR>
<PRE>
<FONT SIZE=2>/*
// ----- Archivo: Ejemplo12.java
*/
import java.io.*;
import java.awt.*;
import java.applet.*;
public class Ejemplo12 extends Applet {
public void init() {
new Ventana12();
}
}
/*
// -------- Esta clase es la que en realidad hace el trabajo
*/
class Ventana12 extends Frame {
TextArea contenido;
Button cerrar;
Ventana12() {
super("Ejemplo de E/S");
contenido = new TextArea();
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -