Home » diciembre 2013
Definición de una clase en Java

clase en Java
Definición de una clase en Java a.) Introducción El fundamento básico de la programación enfocada a objetos en Java es la clase. Una clase determina la manera y comportamiento de un objeto. Para crear una clase solo se requiere un archivo fuente que contenga la palabra clave reservada class seguida de un identificador legal y un bloque delimitado por dos llaves para el cuerpo de la clase. class MiPunto { } Un archivo de Java debe tener el mismo nombre que la clase que contiene, y se les suele asignar la expansión ".java". Por ejemplo la clase MiPunto se guardaria en un fichero que se llamase MiPunto.java. Hay que tener presente que en Java se diferencia entre mayusculas y minusculas; el nombre de la clase y el de archivo fuente han de ser exactamente iguales. Aunque la clase MiPunto es sintacticamente correcta, es lo que se viene a llamar una clase vacia, es decir, una clase que no hace nada. Las clases tipicas de Java incluiran variables y metodos de instancia. Los proyectos en Java completos constaran por lo comun de algunas clases de Java en diferentes ficheros fuente. Una clase es una plantilla para un objeto. Por lo tanto determina la articula de un objeto y su interfaz funcional, en manera de metodos. Cuando se ejecuta un proyecto en Java, el sistema emplea definiciones de clase para crear instancias de las clases, que son los objetos reales. Los terminos instancia y objeto se emplean de manera indistinta. La manera común de una definicion de clase es: class Nombre_De_Clase { tipo_de_variable nombre_de_atributo1; tipo_de_variable nombre_de_atributo2; // . . . tipo_devuelto nombre_de_método1( lista_de_parámetros ) { cuerpo_del_método1; } tipo_devuelto nombre_de_método2( lista_de_parámetros ) { cuerpo_del_método2; } // . . . } Los tipos tipo_de_variable y tipo_devuelto, han de ser tipos simples Java o nombres de otras clases ya definidas. Tanto Nombre_De_Clase, como los nombre_de_atributo y nombre_de_método, han de ser identificadores Java válidos. b.) Los atributos Los datos se encapsulan dentro de una clase declarando variables dentro de las llaves de apertura y cierre de la declaración de la clase, variables que se conocen como atributos. Se declaran idéntico que las variables locales de un método en concreto. Por ejemplo, este es un proyecto que declara una clase MiPunto, con dos atributos enteros llamados x e y. class MiPunto { int x, y; } Los atributos se pueden declarar con dos clases de tipos: un tipo simple Java (ya descritos), o el nombre de una clase (será una referencia a objeto, véase el punto C.a de este mismo apartado). Cuando se realiza una instancia de una clase (creacion de un objeto) se reservara en la memoria un lugar para un conjunto de datos como el que determinan los atributos de una clase. A este conjunto de variables se le designa variables de instancia. c.) Los métodos Los métodos son subrutinas que determinan la interfaz de una clase, sus capacidades y comportamiento. Un método ha de tener por nombre cualquier identificador legal diferente de los ya utilizados por los nombres de la clase en que está definido. Los métodos se declaran al mismo nivel que las variables de instancia dentro de una definición de clase. En la declaración de los métodos se determina el tipo de valor que devuelven y a una lista maneral de parámetros de entrada, de sintaxis tipo identificador separadas por comas. La manera común de una declaración de método es: tipo_devuelto nombre_de_método( lista-formal-de-parámetros ) { cuerpo_del_método; } Por ejemplo el próximo metodo devuelve la suma de dos enteros: int metodoSuma( int paramX, int paramY ) { return ( paramX + paramY ); } En el caso de que no se desee devolver ningún valor se deberá indicar como tipo la palabra reservada void. Así mismo, si no se quieren parámetros, la declaración del método debería incluir un par de paréntesis vacíos (sin void): void metodoVacio( ) { }; Los metodos son llamados señalando una instancia individual de la clase, que tendra su propio conjunto unico de variables de instancia, por lo que los metodos se pueden mencionar directamente a ellas. El método inicia() para establecer valores a las dos variables de instancia sería el siguiente: void inicia( int paramX, int paramY ) { x = paramX; y = paramY; }

El polimorfismo en Java

polimorfismo en Java
El polimorfismo en Java a.) Selección dinámica de método Las dos clases implementadas a continuación tienen una relación subclase/superclase simple con un único método que se sobrescribe en la subclase: class claseAA { void metodoDinamico() { System.out.println("En el metodo dinamico de claseAA"); } } class claseBB extends claseAA { void metodoDinamico() { System.out.println("En el metodo dinamico de claseBB"); } } Por lo tanto si ejecutamos: claseAA referenciaAA = new claseBB(); referenciaAA.metodoDinamico(); La salida de este proyecto es: En el metodo dinamico de claseBB Se declara la variable de tipo claseA, y después se almacena una referencia a una instancia de la clase claseB en ella. Al llamar al método metodoDinamico() de claseA, el compilador de Java verifica que claseA tiene un método llamado metodoDinamico(), pero el intérprete de Java observa que la referencia es realmente una instancia de claseB, por lo que llama al método metodoDinamico() de claseB en vez de al de claseA. Esta manera de polimorfismo dinamico en tiempo de ejecucion es uno de los mecanismos mas poderosos que proporciona el diseño orientado a objetos para soportar la reutilizacion del codigo y la robustez. b.) Sobrescritura de un método Mientras una jerarquia de herencia puede interesar regresar a escribir el cuerpo de un metodo, para hacer una funcionalidad de distinto forma dependiendo del nivel de abstraccion en que nos encontremos. A esta transformación de funcionalidad se le llama sobrescritura de un metodo. Por ejemplo, en una herencia entre una clase SerVivo y una clase hija Persona; si la clase SerVivo tuviese un metodo alimentarse(), deberia regresar a escribirse en el nivel de Persona, ya que que una persona no se alimenta ni como un Animal, ni como una Planta... La mejor forma de contemplar la diferencia entre sobrescritura y sobrecarga es mediante un ejemplo. A continuacion se puede contemplar la implementacion de la sobrecarga de la distancia en 3D y la sobrescritura de la distancia en 2D. class MiPunto3D extends MiPunto { int x,y,z; double distancia(int pX, int pY) { // Sobrescritura int retorno=0; retorno += ((x/z)-pX)*((x/z)-pX); retorno += ((y/z)-pY)*((y/z)-pY); return Math.sqrt( retorno ); } } Se inician los objetos mediante las sentencias: MiPunto p3 = new MiPunto(1,1); MiPunto p4 = new MiPunto3D(2,2); Y llamando a los metodos de la próximo forma: p3.distancia(3,3); //Método MiPunto.distancia(pX,pY) p4.distancia(4,4); //Método MiPunto3D.distancia(pX,pY) Los métodos se seleccionan en función del tipo de la instancia en tiempo de ejecución, no a la clase en la cual se está ejecutando el método actual. A esto se le llama selección dinámica de método. c.) Sobrecarga de método Es probable que necesitemos crear mas de un metodo con el mismo nombre, pero con listas de parametros distintas. A esto se le llama sobrecarga del metodo. La sobrecarga de metodo se emplea para proporcionar a Java un comportamiento polimorfico. Un ejemplo de uso de la sobrecarga es por ejemplo, el crear constructores alternativos en función de las coordenadas, tal y como se hacía en la clase MiPunto: MiPunto( ) { //Constructor por defecto inicia( -1, -1 ); } MiPunto( int paramX, int paramY ) { // Parametrizado this.x = paramX; y = paramY; } Se llama a los constructores basandose en el numero y tipo de parametros que se les pase. Al numero de parametros con tipo de una secuencia especifica se le llama signatura de tipo. Java emplea estas signaturas de tipo para determinar a que metodo llamar. Para diferenciar entre dos metodos, no se estiman los nombres de los parametros formales sino sus tipos: MiPunto p1 = new MiPunto(); // Constructor por defecto MiPunto p2 = new MiPunto( 5, 6 ); // Constructor parametrizado d.) Limitación de la sobreescritura: final Todos los metodos y las variables de instancia se pueden sobrescribir por defecto. Si se desea declarar que ya no se desea permitir que las subclases sobrescriban las variables o metodos, estos se pueden declarar como final. Esto se emplea a menudo para crear el equivalente de una constante de C++. Es un convenio de codificacion habitual escoger identificadores en mayusculas para las variables que sean final, por ejemplo: final int NUEVO_ARCHIVO = 1; d. las referencias polimórficas: this y super a.) Entrada a la particular clase: this Aunque ya se explicó en el artículo de este tutorial el uso de la referencia this como modificador de ámbito, también se la puede nombrar como ejemplo de polimorfismo Ademas de realizar continua referencia a la clase en la que se invoque, tambien vale para sustituir a sus constructores, utilizandola como metodo: this(); // Constructor por defecto this( int paramX, int paramY ); // Constructor parametrizado b.) Entrada a la superclase: super Ya hemos visto el funcionamiento de la referencia this como referencia de un objeto hacia si mismo. En Java tiene lugar otra referencia llamada super, que se refiere directamente a la superclase. La referencia super usa para alcanzar a metodos o atributos de la superclase. Podiamos haber implementado el constructor de la clase MiPunto3D (hija de MiPunto) de la próximo forma: MiPunto3D( int x, int y, int z ) { super( x, y ); // Aquí se llama al constructor de MiPunto this.z = super.metodoSuma( x, y ); // Método de la superclase } Con una sentencia super.metodoSuma(x, y) se llamaría al método metodoSuma() de la superclase de la instancia this. Por el opuesto con super() llamamos al constructor de la superclase.

Acceso al objeto en Java

objeto en Java
Entrada al objeto en Java a.) El operador punto (.) El operador punto (.) se emplea para alcanzar a las variables de instancia y los metodos contenidos en un objeto, mediante su referencia a objeto: referencia_a_objeto.nombre_de_variable_de_instancia referencia_a_objeto.nombre_de_método( lista-de-parámetros ); Hemos creado un ejemplo completo que combina los operadores new y punto para crear un objeto MiPunto, Guardar algunos valores en él e imprimir sus valores finales: MiPunto p6 = new MiPunto( 10, 20 ); System.out.println ("p6.- 1. X=" + p6.x + " , Y=" + p6.y); p6.inicia( 30, 40 ); System.out.println ("p6.- 2. X=" + p6.x + " , Y=" + p6.y); Cuando se ejecuta este programa, se observa la próximo salida: p6.- 1. X=10 , Y=20 p6.- 2. X=30 , Y=40 Mientras las impresiones (método println()) se accede al valor de las variables mediante p6.x y p6.y, y entre una impresión y otra se llama al método inicia(), cambiando los valores de las variables de instancia. Este es uno de los apariencias mas significativos de la diferencia entre la programacion enfocada a objetos y la programacion estructurada. Cuando se llama al metodo p6.inicia(), lo primero que se hace en el metodo es sustituir los nombres de los atributos de la clase por las correspondientes variables de instancia del objeto con que se ha llamado. Asi por ejemplo x se convertira en p6.x. Si otros objetos llaman a inicia(), inclusive si lo hacen de una forma concurrente, no se producen efectos laterales, ya que las variables de instancia sobre las que laboran son distintas. b.) La referencia this Java incluye un valor de referencia especial llamado this, que se emplea dentro de cualquier metodo para mencionarse al objeto actual. El valor this se refiere al objeto sobre el que ha sido llamado el metodo actual. Se puede emplear this siempre que se requiera una referencia a un objeto del tipo de una clase actual. Si hay dos objetos que utilicen el mismo codigo, seleccionados a traves de otras instancias, cada uno tiene su propio valor unico de this. Un refinamiento habitual es que un constructor llame a otro para desarrollar la instancia correctamente. El próximo constructor llama al constructor parametrizado MiPunto(x,y) para terminar de empezar la instancia: MiPunto() { this( -1, -1 ); // Llama al constructor parametrizado } En Java se faculta declarar variables locales, incluyendo parametros formales de metodos, que se solapen con los nombres de las variables de instancia. No se emplean x e y como nombres de parametro para el metodo inicia, porque ocultarian las variables de instancia x e y reales del entorno del metodo. Si lo hubiesemos hecho, entonces x se debiera referido al parametro formal, ocultando la variable de instancia x: void inicia2( int x, int y ) { x = x; // Ojo, no modificamos la variable de instancia!!! this.y = y; // Modificamos la variable de instancia!!! }

GESTIÓN DE EXCEPCIONES Y ERRORES en Java

ERRORES en Java
GESTIÓN DE EXCEPCIONES Y ERRORES en Java A. Introducción El control de flujo en un proyecto Java puede hacerse mediante las ya conocidas sentencias estructuradas (if, while, return). Pero Java va mucho mas alla, mediante una tecnica de proyectocion denominada gestion de excepciones. Mediante las excepciones se podra eludir repetir continuamente codigo, en busca de un probable error, y avisar a otros objetos de una clausula anormal de ejecucion mientras un programa. Mientras este capitulo estudiaremos la gestion de excepciones y errores, sin pretender profundizar demasiado, pero si fijando la fundamento conceptual de lo que este modo de programacion supone. Mediante la gestión de excepciones se prescindirá de sentencias de control de errores del tipo: if ( yerro == true ) return ERROR; B. Tipos de excepciones Tienen lugar varios tipos fundamentales de excepciones: Error: Excepciones que indican dificultades muy graves, que suelen ser no recuperables y no deben casi jamás ser capturadas. Exception: Excepciones no definitivas, pero que se detectan afuera del tiempo de ejecucion. RuntimeException: Excepciones que se dan mientras la ejecucion del programa. Imagen 5: Herencia de excepciones Java Todas las excepciones tienen como clase fundamento la clase Throwable, que esta incluida en el paquete java.lang, y sus metodos son: Trowable( String mensaje ); Constructor. La cadena es opcional Throwable fillInStackTrace(); Llena la pila de dibuja de ejecución. String getLocalizedMessage(); Crea una descripción local de este objeto. String getMessage(); Devuelve la cadena de yerro del objeto. void printStackTrace( PrintStream_o_PrintWriter s ); Imprime este objeto y su dibuja en el flujo del parámetro s, o en la salida estándar (por defecto). String toString; Devuelve una breve descripción del objeto. C. Funcionamiento a.) Introducción Para que el sistema de gestion de excepciones funcione, se ha de laborar en dos fracciónes de los programas: Definir que fracciones de los proyectos crean una excepcion y debajo que condiciones. Para ello se emplean las palabras reservadas throw y throws. Verificar en ciertas fracciones de los proyectos si una excepcion se ha producido, y actuar en consecuencia. Para ello se emplean las palabras reservadas try, catch y finally. b.) Empleo de excepciones: try - catch - finally Cuando el programador va a ejecutar un pedazo de codigo que pueda provocar una excepcion (por ejemplo, una lectura en un fichero), debe incluir este pedazo de codigo dentro de un bloque try: try { // Código seguramente problemático } Pero lo significativo es como controlar que realizar con la probable excepcion que se cree. Para ello se emplean las condiciones catch, en las que se especifica que accion realizar: try { // Código seguramente problemático } catch( tipo_de_excepcion e) { // Código para solucionar la excepción e } catch( tipo_de_excepcion_mas_general e) { // Código para solucionar la excepción e } En el ejemplo se observa que se pueden anidar sentencias catch, pero conviene realizarlo señalando en ultimo espacio las excepciones mas globales (es decir, que se encuentren mas encima en el arbol de herencia de excepciones), porque el interprete Java ejecutara aquel bloque de codigo catch cuyo parametro sea del tipo de una excepcion lanzada. Si por ejemplo se intentase capturar primero una excepcion Throwable, jamas llegariamos a gestionar una excepcion Runtime, ya que que cualquier clase hija de Runtime es tambien hija de Throwable, por herencia. Si no se ha lanzado ninguna excepción el código continúa sin ejecutar ninguna sentencia catch. Pero, ¿y si quiero hacer una accion general a todas las opciones?. Para insertar pedazos de codigo que se ejecuten tras la gestion de las excepciones. Este codigo se ejecutara tanto si se ha tratado una excepcion (catch) como sino. Este tipo de codigo se inserta en una sentencia finally, que sera ejecutada tras el bloque try o catch: try { } catch( Exception e ) { } finally { // Se ejecutara tras try o catch } c.) Lanzamiento de excepciones: throw - throws Muchas veces el programador dentro de un algun metodo debera verificar si cierta clausula de excepcion se cumple, y si es asi lanzarla. Para ello se emplean las palabras reservadas throw y throws. Por una fracción la excepcion se lanza mediante la sentencia throw: if ( condicion_de_excepcion == true ) throw new miExcepcion(); Se puede contemplar que hemos creado un objeto de la clase miExcepcion, ya que que las excepciones son objetos y por tanto deberan ser instanciadas antes de ser lanzadas. Aquellos metodos que pueden arrojar excepciones, deben cuales son esas excepciones en su declaracion. Para ello se emplea la sentencia throws: tipo_devuelto miMetodoLanzador() throws miExcep1, miExcep2 { // Codigo capaz de arrojar excepciones miExcep1 y miExcep2 } Se puede contemplar que cuando se pueden arrojar en el metodo mas de una excepcion se deben indicar en su declaracion separadas por comas. d.) Ejemplo de gestión de excepciones Ahora que ya conocemos como funciona este sistema, conviene ver al menos un chico ejemplo, que instruído al lector en el uso de las excepciones: // Creo una excepción personalizada class MiExcepcion extends Exception { MiExcepcion(){ super(); // constructor por defecto de Exception } MiExcepcion( String cadena ){ super( cadena ); // constructor param. de Exception } } // Esta clase lanzará la excepción class Lanzadora { void lanzaSiNegativo( int param ) throws MiExcepcion { if ( param < 0 ) throw new MiExcepcion( "Numero negativo" ); } } class Excepciones { public static void main( String[] args ) { // Para leer un fichero Lanzadora lanza = new Lanzadora(); FileInputStream acceso = null; int leo; try { acceso = new FileInputStream( "fich.txt" ); while ( ( leo = entrada.read() ) != -1 ) lanza.lanzaSiNegativo( leo ); entrada.close(); System.out.println( "Todo fuese bien" ); } catch ( MiExcepcion e ){ // Personalizada System.out.println( "Excepcion: " + e.getMessage() ); } catch ( IOException e ){ // Estándar System.out.println( "Excepcion: " + e.getMessage() ); } finally { if ( acceso != null ) try { entrada.close(); // Siempre queda cerrado } catch ( Exception e ) { System.out.println( "Excepcion: " + e.getMessage() ); } System.out.println( "Fichero cerrado." ); } } } class Excepciones { public static void main( String[] args ) { // Para leer un fichero FileInputStream acceso = null; Lanzadora lanza = new Lanzadora(); int leo; try { acceso = new FileInputStream("fich.txt"); while ( ( leo = entrada.read() ) != -1 ) lanza.lanzaSiNegativo( leo ); System.out.println( "Todo fuese bien" ); } catch ( MiExcepcion e ){ // Personalizada System.out.println( "Excepcion: " + e.getMessage() ); } catch ( IOException e ){ // Estándar System.out.println( "Excepcion: " + e.getMessage() ); } finally { entrada.close(); // Así el fichero siempre queda cerrado System.out.println( "Fichero cerrado" ); } } } Este proyecto lee un fichero (fichero.txt), y lee su contenido en manera de numeros. Si sdeterminados de los numeros leidos es negativo, lanza una excepcion MiExcepcion, Asimismo gestiona la excepcion IOException, que es una excepcion de las que Java incluye y que se lanza si hay determinado asunto en una operacion de entrada/salida. Ambas excepciones son gestionadas, imprimiendo su contenido (cadena de error) por pantalla. La salida de este programa, suponiendo un número negativo sería: Excepcion: Numero negativo Fichero cerrado En el caso de que no debiera ningun numero negativo seria: Todo fuese bien Fichero cerrado En el caso de que se produjese un yerro de E/S, al leer el primer número, sería: Excepcion: java.io.IOException Fichero cerrado e.) Conclusiones En cualquier caso se recomienda al proyectodor no abusar de este sistema como control de flujos simples, sino usarlo solo en aquellos estados del proyecto que realmente creen un asunto de ejecucion que pueda ser letal para el proyecto. Para más información sobre las excepciones Java, véanse [Zolli, 1997] y [Naughton, 1996]. D. Excepciones que incorpora Java 1.2 a.) Clases de Yerro LinkageError: Una clase no satisface la dependencia que tiene respecto a otra. ClassCircularityError: Se detectó una herencia circular entre clases. ClassFormatError: Una clase cargada no ha sido incompletamente descrita. UnsupportedClassVersionError: La versión de una clase no es correcta. ExceptionInInitializerYerro: Yerro al empezar un miembro static. IncompatibleClassChangeError: En una clase, su interfaz no es idéntico al declarado AbstractMethodError: Se ha invocado un método abstracto. IllegalAccessError: La aplicacion intento alcanzar a determinado miembro no visible. InstantiationError: Se intentó instanciar una clase abstracta o interfaz. NoSuchFieldError: No se encontró algun atributo. NoSuchMethodError: No se encontró algun método. NoClassDefFoundError: No se encontró una clase cuando se necesitaba. UnsatisfiedLinkError: Se encontró un enlace insatisfecho en un método nativo. VerifyError: Se ha producido un yerro de verificación al cargar una clase. ThreadDeath: Se ha lanzado en el thread víctima tras llamar a stop(). VirtualMachineError: La máquina virtual se ha averiado o quedado sin recursos. InternalYerro: Yerro interno en tiempo de ejecución. OutOfMemoryError: El lector ha agotado la memoria. StackOverflowError: Desbordamiento de pila. ¿Recursión infinita?. UnknownError: Gravisimo yerro desconocido. b.) Clases de Exception CloneNotSupportedException: No se pudo copiar un objeto mediante clone(). IllegalAccessException: Algún método invocado es no visible. InstantiationException: Se ha intentado instanciar una interfaz o una clase abstracta. InterruptedException: Cuando se invoca a interrupt() sobre un thread dormido. NoSuchFieldException: La clase no tiene un atributo con ese nombre. NoSuchMethodException: La clase no tiene un método con ese nombre. c.) Clases de RuntimeException ArithmeticException: Yerro de cálculo (como división por cero...). ArrayStoreException: Intento de Guardar un objeto equivocado en un vector. ClassCastException: Intento de conversión inválida. IllegalArgumentException: Se ha pasado un argumento inválido a un método: IllegalThreadStateException: Un thread no estaba en el estado adecuado. NumberFormatException: Una cadena contenedora de un número, no lo contiene. IllegalMonitorStateException: Se ha usado wait/notify afuera de codigo sincronizado. IllegalStateException: Método invocado en un momento inapropiado. IndexOutOfBoundsException: Entrada a un vector afuera de sus limites: ArrayIndexOutOfBoundsException: Idem, para una matriz. StringIndexOutOfBoundsException: Idem, para una cadena. NegativeArraySizeException: Intento de creacion de un vector de dimensión negativo. NullPointerException: Se ha usado una referencia null para alcanzar a un campo. SecurityException: Algo ha sido vedado por el sistema de seguridad. UnsupportedOperationException: Una operación invocada no se soporta. Para más información véase la documentación del JDK que usted vaya a utilizar.

Herencia múltiple en Java

Herencia múltiple en Java
Herencia múltiple en Java Java es un lenguaje que incorpora herencia simple de implementacion pero que puede aportar herencia multiple de interfaz. Esto permite la herencia multiple en el diseño de los proyectos Java. Una interfaz puede heredar de más de una interfaz antecesora. interface InterfazMultiple extends Interfaz1,Interfaz2{ } Una clase no puede tener más que una clase antecesora, pero puede implementar más de una interfaz: class MiClase extends SuPadre implements Interfaz1,Interfaz2{ } El ejemplo tipico de herencia multiple es el que se muestra con la herencia en diamante: Imagen 6: Ejemplo de herencia múltiple Para poder llevar a cabo un esquema como el previo en Java es indispensable que las clases A, B y C de la figura sean interfaces, y que la clase D sea una clase (que recibe la herencia multiple): interface A{ } interface B extends A{ } interface C extends A{ } class D implements B,C{ } E. Colisiones en la herencia múltiple En una herencia multiple, los identificadores de determinadoos metodos o atributos pueden coincidir en la clase que hereda, si dos de las interfaces padres tienen determinado metodo o atributo que coincida en nombre. A esto se le llama colision. Esto se dara cuando las clases padre (en el ejemplo previo B y C) tienen un atributo o metodo que se llame igual. Java resuelve el asunto estableciendo una serie de reglas. Para la colision de nombres de atributos, se obliga a especificar a que interfaz fundamento pertenecen al utilizarlos. Para la colisión de nombres en métodos: Si tienen el mismo nombre y distintos parametros: se produce sobrecarga de metodos permitiendo que existan algunas formas de llamar al mismo. Si solo varia el valor devuelto: se da un yerro de compilacion, señalando que no se pueden implementar los dos. Si coinciden en su declaración: se elimina uno de los dos, con lo que sólo queda uno. F. Envolturas de los tipos simples Los tipos de datos de Java no forman fraccion de la jerarquia de objetos. Sin embargo a veces es indispensable crear una representacion como objeto de sdeterminados de los tipos de datos simples de Java. La API de Java contiene un conjunto de interfaces especiales para adaptar el comportamiento de los tipos de datos simple. A estas interfaces se las conoce como envolturas de tipo simple. Todas ellas son hijas de la clase abstracta Number y son: Double: Da soporte al tipo double. Float: Da soporte al tipo float. Integer: Da soporte a los tipos int, short y byte. Long: Da soporte al tipo long. Character: Envoltura del tipo char. Boolean: Envoltorio al tipo boolean.

INTERFACES en Java

INTERFACES en Java
INTERFACES en Java A. Introducción Las interfaces Java son expresiones puras de diseño. Se trata de autenticas conceptualizaciones no implementadas que sirven de guia para definir un algun concepto (clase) y lo que debe hacer, pero sin construir un mecanismo de solucion. Se trata de declarar metodos abstractos y persistentes que posteriormente puedan ser implementados de distintos formas segun las necesidades de un programa. Por ejemplo una misma interfaz podria ser implementada en una version de prueba de forma escaso optima, y ser acelerada convenientemente en la version definitiva tras conocer mas a fondo el problema. B. Declaración Para declarar una interfaz se emplea la sentencia interface, de la misma forma que se usa la sentencia class: interface MiInterfaz { int CONSTANTE = 100; int metodoAbstracto( int parametro ); } Se observa en la declaracion que las variables adoptan la declaracion en mayusculas, pues en verdad actuaran como persistentes final. En ningun caso estas variables actuaran como variables de instancia. Por su parte, los metodos tras su declaracion presentan un punto y coma, en espacio de su cuerpo entre llaves. Son metodos abstractos, por tanto, metodos sin implementacion C. Implementación de una interfaz Como ya se ha visto, las interfaces carecen de funcionalidad por no estar implementados sus metodos, por lo que se requiere determinado mecanismo para dar cuerpo a sus metodos. La palabra reservada implements utilizada en la declaracion de una clase indica que la clase implementa la interfaz, es decir, que asume las persistentes de la interfaz, y codifica sus metodos: class ImplementaInterfaz implements MiInterfaz{ int multiplicando=CONSTANTE; int metodoAbstracto( int parametro ){ return ( parametro * multiplicando ); } } En este ejemplo se observa que han de codificarse todos los metodos que decide la interfaz (metodoAbstracto()), y la validez de las persistentes (CONSTANTE) que determina la interfaz mientras toda la declaracion de la clase. Una interfaz no puede implementar otra interfaz, aunque sí extenderla (extends) ampliándola.

La clase Object en Java

La clase Object en Java
La clase Object en Java La clase Object es la superclase de todas las clases da Java. Todas las clases derivan, directa o indirectamente de ella. Si al definir una nueva clase, no surge la condicion extends, Java estima que felicidad clase desciende directamente de Object. La clase Object aporta una serie de funciones escenciales comunes a todas las clases: public boolean equals( Object obj ): Se emplea para comparar, en valor, dos objetos. Devuelve true si el objeto que recibe por parametro es igual, en valor, que el objeto desde el que se llama al metodo. Si se quieren comparar dos referencias a objeto se pueden emplear los operadores de comparacion == y !=. public int hashCode(): Devuelve un código hash para ese objeto, para poder almacenarlo en una Hashtable. protected Object clone() throws CloneNotSupportedException: Devuelve una copia de ese objeto. public final Class getClass(): Devuelve el objeto concreto, de tipo Class, que representa la clase de ese objeto. protected void finalize() throws Trowable: Realiza acciones mientras la recogida de basura.

la composición en Java

la composición en Java
la composición en Java Otro tipo de relacion muy habitual en los diseños de los proyectos es la composicion. Los objetos suelen estar compuestos de conjuntos de objetos mas pequeños; un coche es un conjunto de motor y carroceria, un motor es un conjunto de piezas, y asi sucesivamente. Este concepto es lo que se conoce como composicion. La manera de implementar una relación de composición en Java es incluyendo una referencia a objeto de la clase componedora en la clase compuesta. Por ejemplo, una clase AreaRectangular, quedaría definida por dos objetos de la clase MiPunto, que representasen dos puntas contrarias de un rectángulo: class AreaRectangular { MiPunto extremo1; //extremo inferior izquierdo MiPunto extremo2; //extremo sobresaliente derecho AreaRectangular() { extremo1=new MiPunto(); extremo2=new MiPunto(); } boolean estaEnElArea( MiPunto p ){ if ( ( p.x>=extremo1.x && p.x<=extremo2.x ) && ( p.y>=extremo1.y && p.y<=extremo2.y ) ) return true; else return false; } } Puede observarse que las referencias a objeto (extremo1 y extremo2) son iniciadas, instanciando un objeto para cada una en el constructor. Asi esta clase mediante dos puntos, referenciados por extremo1 y extremo2, constituye unos limites de su area, que seran utilizados para verificar si un punto esta en su area en el metodo estaEnElArea().

La destrucción de objetos en Java

La destrucción de objetos en Java
La destrucción de objetos en Java a.) La destrucción de los objetos Cuando un objeto no va a ser empleado, el lugar de memoria de dinamica que emplea ha de ser liberado, asi como los recursos que poseia, permitiendo al proyecto disponer de todos los recursos posibles. A esta accion se la da el nombre de destruccion del objeto. En Java la destrucción se puede hacer de manera automática o de manera personalizada, en función de las características del objeto. b.) La destrucción por defecto: Recogida de basura El interprete de Java posee un sistema de recogida de basura, que por lo comun faculta que no nos preocupemos de liberar la memoria asignada explicitamente. El recolector de basura sera el encargado de liberar una zona de memoria dinamica que habia sido reservada mediante el operador new, cuando el objeto ya no va a ser utilizado mas mientras el proyecto (por ejemplo, sale del entorno de utilizacion, o no es referenciado nuevamente). El sistema de recogida de basura se ejecuta periódicamente, buscando objetos que ya no estén referenciados. c.) La destrucción personalizada: finalize A veces una clase mantiene un medio que no es de Java como un descriptor de archivo o un tipo de letra del sistema de ventanas. En este caso seria acertado el utilizar la finalizacion explicita, para asegurar que dicho medio se libera. Esto se hace mediante la destruccion personalizada, un sistema parecida a los destructores de C++. Para especificar una destruccion personalizada se agrega un metodo a la clase con el nombre finalize: class ClaseFinalizada{ ClaseFinalizada() { // Constructor // Reserva del medio no Java o medio compartido } protected void finalize() { // Liberacion del medio no Java o medio compartido } } El interprete de Java llama al metodo finalize(), si tiene lugar cuando vaya a reclamar el lugar de ese objeto, mediante la recogida de basura. Debe observarse que el método finalize() es de tipo protected void y por lo tanto deberá de sobreescribirse con este mismo tipo.

LA HERENCIA en Java

HERENCIA en Java
LA HERENCIA en Java A. Introducción La verdadera potencia de la programacion enfocada a objetos radica en su capacidad para reflejar la abstraccion que el cerebro humano realiza automaticamente mientras el proceso de aprendizaje y el proceso de analisis de informacion. Las personas percibimos la verdad como un conjunto de objetos interrelacionados. Felicidades interrelaciones, pueden verse como un conjunto de abstracciones y generalizaciones que se han ido asimilando desde la niñez. Asi, los defensores de la programacion enfocada a objetos afirman que esta tecnica se adecua mejor al funcionamiento del cerebro humano, al permitir descomponer un asunto de alguna magnitud en un conjunto de asuntos menores subordinados del primero. La capacidad de descomponer un asunto o concepto en un conjunto de objetos relacionados entre si, y cuyo comportamiento es facilmente identificable, puede ser muy provechoso para el desarrollo de proyectos informaticos. B. Jerarquía La herencia es el mecanismo importante de relacion entre clases en la orientacion a objetos. Relaciona las clases de forma jerarquica; una clase padre o superclase sobre otras clases hijas o subclases. Imagen 4: Ejemplo de otro árbol de herencia Los descendientes de una clase heredan todas las variables y metodos que sus ascendientes hayan especificado como heredables, asimismo de crear los suyos propios. La caracteristica de herencia, nos faculta definir nuevas clases derivadas de otra ya existente, que la especializan de cierta manera. Asi logramos definir una jerarquia de clases, que se puede presentar mediante un arbol de herencia. En todo lenguaje orientado a objetos tiene lugar una jerarquia, mediante la que las clases se relacionan en terminos de herencia. En Java, el punto mas alto de la jerarquia es la clase Object de la cual derivan todas las demas clases. C. Herencia múltiple En la orientacion a objetos, se estiman dos tipos de herencia, simple y multiple. En el caso de la primera, una clase solo puede derivar de una unica superclase. Para el segundo tipo, una clase puede descender de algúnas superclases. En Java solo se dispone de herencia simple, para una gran sencillez del lenguaje, si bien se compensa de alguna forma la inexistencia de herencia multiple con un concepto denominado interface, que estudiaremos mas adelante. D. Declaración Para indicar que una clase deriva de otra, heredando sus propiedades (metodos y atributos), se usa el termino extends, como en el próximo ejemplo: public class SubClase extends SuperClase { // Contenido de la clase } Por ejemplo, creamos una clase MiPunto3D, hija de la clase ya mostrada MiPunto: class MiPunto3D extends MiPunto { int z; MiPunto3D( ) { x = 0; // Heredado de MiPunto y = 0; // Heredado de MiPunto z = 0; // Nuevo atributo } } La palabra clave extends se emplea para decir que queremos crear una subclase de la clase que es nombrada a continuacion, en vuestro caso MiPunto3D es hija de MiPunto.

La instanciación de las clases, Los objetos en Java

Los objetos en Java
La instanciación de las clases: Los objetos en Java a.) Referencias a Objeto e Instancias Los tipos simples de Java describian el dimension y los valores de las variables. Cada vez que se crea una clase se agrega otro tipo de dato que se puede utilizar idéntico que uno de los tipos simples. Por ello al declarar una nueva variable, se puede utilizar un nombre de clase como tipo. A estas variables se las conoce como referencias a objeto. Todas las referencias a objeto son compatibles tambien con las instancias de subclases de su tipo. Del mismo modo que es adecuado asignar un byte a una variable declarada como int, se puede declarar que una variable es del tipo MiClase y guardar una referencia a una instancia de este tipo de clase: MiPunto p; Esta es una declaración de una variable p que es una referencia a un objeto de la clase MiPunto, de momento con un valor por defecto de null. La referencia null es una referencia a un objeto de la clase Object, y se podrá convertir a una referencia a cualquier otro objeto porque todos los objetos son hijos de la clase Object. b.) Constructores Las clases pueden implementar un método especial llamado constructor. Un constructor es un método que comienza un objeto inmediatamente después de su creación. De esta manera nos evitamos el tener que comienzar las variables explícitamente para su comienzación. El constructor tiene exactamente el mismo nombre de la clase que lo implementa; no puede haber ningún otro método que comparta su nombre con el de su clase. Una vez definido, se llamará automáticamente al constructor al crear un objeto de esa clase (al utilizar el operador new). El constructor no devuelve ningún tipo, ni siquiera void. Su misión es empezar todo estado interno de un objeto (sus atributos), haciendo que el objeto sea utilizable inmediatamente; reservando memoria para sus atributos, iniciando sus valores... Por ejemplo: MiPunto( ) { inicia( -1, -1 ); } Este constructor denominado constructor por defecto, por no tener parametros, constituye el valor -1 a las variables de instancia x e y de los objetos que construya. El compilador, por defecto ,llamará al constructor de la superclase Object() si no se especifican parámetros en el constructor. Este otro constructor, sin embargo, recibe dos parámetros: MiPunto( int paraX, int paraY ) { inicia( paramX, paramY ); } La lista de parametros especificada despues del nombre de una clase en una sentencia new se emplea para pasar parametros al constructor. Se llama al método constructor justo después de crear la instancia y antes de que new devuelva el control al punto de la llamada. Asi, cuando ejecutamos el próximo programa: MiPunto p1 = new MiPunto(10, 20); System.out.println( "p1.- x = " + p1.x + " y = " + p1.y ); Se presenta en la pantalla: p1.- x = 10 y = 20 Para crear un proyecto Java que contenga ese codigo, se debe de crear una clase que contenga un metodo main(). El interprete java se ejecutara el metodo main de la clase que se le indique como parametro. Para mas informacion sobre como crear y ejecutar un programa, asi como los tipos de proyectos que se pueden crear en Java, vease el capitulo "II.12. Creacion de proyectos Java" de este tutorial. c.) El operador new El operador new crea una instancia de una clase (objetos) y devuelve una referencia a ese objeto. Por ejemplo: MiPunto p2 = new MiPunto(2,3); Este es un ejemplo de la creación de una instancia de MiPunto, que es controlador por la referencia a objeto p2. Hay una distincion apreciación entre la manera de manipular los tipos simples y las clases en Java: Las referencias a objetos realmente no contienen a los objetos a los que referencian. De esta manera se pueden crear multiples referencias al mismo objeto, como por ejemplo: MiPunto p3 =p2; Aunque tan sólo se creó un objeto MiPunto, hay dos variables (p2 y p3) que lo referencian. Cualquier cambio realizado en el objeto referenciado por p2 afectará al objeto referenciado por p3. La asignación de p2 a p3 no reserva memoria ni modifica el objeto. De hecho, las asignaciones posteriores de p2 simplemente desengancharán p2 del objeto, sin afectarlo: p2 = null; // p3 todavía apunta al objeto creado con new Aunque se haya asignado null a p2, p3 todavía apunta al objeto creado por el operador new. Cuando ya no haya ninguna variable que haga referencia a un objeto, Java reclama automaticamente la memoria utilizada por ese objeto, a lo que se designa recogida de basura. Cuando se realiza una instancia de una clase (mediante new) se reserva en la memoria un lugar para un conjunto de datos como el que determinan los atributos de la clase que se indica en la instanciacion. A este conjunto de variables se le designa variables de instancia. La potencia de las variables de instancia es que se obtiene un conjunto diferente de ellas cada vez que se crea un objeto nuevo. Es significativo el entender que cada objeto tiene su particular copia de las variables de instancia de su clase, por lo que los cambios sobre las variables de instancia de un objeto no tienen resultado sobre las variables de instancia de otro. El proximo proyecto crea dos objetos MiPunto y constituye los valores de x e y de cada uno de ellos de forma independiente para presentar que estan realmente separados. MiPunto p4 = new MiPunto( 10, 20 ); MiPunto p5 = new MiPunto( 42, 99 ); System.out.println("p4.- x = " + p4.x + " y = " + p4.y); System.out.println("p5.- x = " + p5.x + " y = " + p5.y); Este es el apariencia de salida cuando lo ejecutamos. p4.- x = 10 y = 20 p5.- x = 42 y = 99

Entradas populares