0% encontró este documento útil (0 votos)
44 vistas104 páginas

Poo 2 Java

Cargado por

Jonathan Michael
Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como PDF, TXT o lee en línea desde Scribd
0% encontró este documento útil (0 votos)
44 vistas104 páginas

Poo 2 Java

Cargado por

Jonathan Michael
Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como PDF, TXT o lee en línea desde Scribd
Está en la página 1/ 104

Tema 2.

Introducción a Java

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Universidad de Málaga

Programación Orientada a Objetos

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 1 / 104
Programación Orientada a Objetos

Tema 2. Introducción a Java


Introducción a Java
Programas y paquetes
Sentencias y expresiones
Control de errores
Elementos del lenguaje
Clases y objetos
Cadenas de caracteres
Arrays
Clases anidadas y enumeraciones
Herencia, polimorfismo y vinculación dinámica
Clases abstractas e interfaces

Esta obra se encuentra bajo una licencia Reconocimiento-NoComercial-CompartirIgual 4.0 Internacional (CC BY-NC-SA 4.0) de Creative Commons.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 2 / 104
Introducción a Java
Desarrollado por Sun (ahora Oracle). Aparece en 1995.
Basado en C++ (y algo en Smalltalk) eliminando:
Definiciones de tipos de valores y macros.
Punteros y aritmética de punteros.
Necesidad de liberar memoria, ya que posee un recolector automático de basura.

Fiable y seguro:
Memoria dinámica automática (no punteros explícitos).
comprobación automática de tamaño de variables.

Orientado a objetos con:


Herencia simple y polimorfismo de datos.
Redefinición de métodos y vinculación dinámica.
Concurrencia integrada en el lenguaje.
Interfaz gráfica integrada en el lenguaje.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 3 / 104
Introducción a Java

El lenguaje de programación Java esta fuertemente asociado con la


Programación Orientada a Objetos (POO).
Se caracteriza por la creación y definición de abstracciones de datos,
denominadas clases, cuyas instancias son entidades activas denominadas
objetos.
La abstracción de datos nos proporciona encapsulación y protección de acceso
a los componentes de las clases.
Además, Java proporciona Herencia simple e Interfaces, redefinición de
métodos, polimorfismo de datos y vinculación dinámica.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 4 / 104
Introducción a Java
Java es un lenguaje que sigue un esquema de traducción mixto:
Los ficheros con código fuente en Java (.java) se compilan a bytecode
(.class).
Los ficheros con código bytecode (.class) son interpretados por la Máquina
Virtual de Java (JVM).
Bibliotecas
(organizadas en paquetes)
.java .class .jar .jar
.class .class
.class .class
.class .class

.java .class
Compilador
Interprete
.java .class JVM

Fuente Bytecode
Java

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 5 / 104
Programa Java

Un programa Java está formado por una o varias clases Java diseñadas para
colaborar en la realización de una tarea.
De entre todas las clases que forman el programa, existe una clase pública
distinguida que contiene un método de clase (estático) que es el punto de
entrada inicial para la ejecución del programa:
public static void main(String[] args) { ... }

Las demás clases, unas pueden estar definidas explícitamente para este
programa, y otras pueden pertenecer a una biblioteca de clases.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 6 / 104
Paquetes Java
En Java, las clases se organizan en paquetes (package).
Los paquetes permiten organizar lógicamente y agrupar clases relacionadas.
El nombre del paquete especifica la jerarquía de directorios (carpetas) donde
se encuentra cada clase.
Todas las clases de un mismo paquete deben estar localizadas en un mismo
directorio (carpeta), organizadas jerárquicamente según el nombre del paquete
al que pertenecen.
Por ejemplo, las clases Punto y Segmento del paquete geometria, la clase Urna del paquete
votacion, la clase Opcion del paquete votacion.datos, y la clase Principal del paquete
anónimo (por defecto).

... espacio−de−trabajo proyecto−1 src geometria Punto.java


Segmento.java

Eclipse
proyecto−2 votacion Urna.java

datos Opcion.java
...
Principal.java

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 7 / 104
Paquetes Java

Usualmente, las clases que definen abstracciones de datos serán definidas


dentro de paquetes determinados, pero las clases distinguidas (definen el
método main) serán definidas en el paquete anónimo (por defecto).
Los paquetes permiten organizar lógicamente y agrupar clases relacionadas.
Si una clase no especifica el paquete al que pertenece, entonces formará parte
del paquete por defecto (anónimo).
Todas las clases que pertenecen a un paquete pueden utilizar directamente,
por sus nombres, a las demás clases que se encuentran en el mismo paquete.
Si una clase quiere utilizar a otra clase que pertenece a otro paquete, entonces
puede hacerlo de dos formas:
Cualificando el nombre de la clase a utilizar con el nombre del paquete al que
pertenece.
Importando la clase a utilizar mediante la sentencia import.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 8 / 104
Paquetes Java

Dada la siguiente especificación de clases, donde ambas clases se definen


dentro del mismo paquete:
// File: paquete1/Punto.java
package paquete1;
public class Punto {
private double x, y;
public Punto() { x = 0; y = 0; }
public Punto(double a, double b) { x = a; y = b; }
// ...
}

// File: paquete1/Segmento.java
package paquete1;
public class Segmento {
private Punto origen, extremo; // utilización directa de Punto
public Segmento(double x1, double y1, double x2, double y2) {
origen = new Punto(x1, y1); // utilización directa de Punto
extremo = new Punto(x2, y2); // utilización directa de Punto
}
// ...
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 9 / 104
Paquetes Java

Sin embargo, si ambas clases se definen en paquetes distintos, es necesario


cualificar o importar el nombre de la clase utilizada:
// File: paquete1/Punto.java
package paquete1;
public class Punto {
private double x, y;
public Punto() { x = 0; y = 0; }
public Punto(double a, double b) { x = a; y = b; }
// ...
}

// File: paquete2/Segmento.java
package paquete2;
public class Segmento {
private paquete1.Punto origen, extremo; // utilización cualificada de Punto
public Segmento(double x1, double y1, double x2, double y2) {
origen = new paquete1.Punto(x1, y1); // utilización cualificada de Punto
extremo = new paquete1.Punto(x2, y2); // utilización cualificada de Punto
}
// ...
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 10 / 104
Paquetes Java

Sin embargo, si ambas clases se definen en paquetes distintos, es necesario


cualificar o importar el nombre de la clase utilizada:
// File: paquete1/Punto.java
package paquete1;
public class Punto {
private double x, y;
public Punto() { x = 0; y = 0; }
public Punto(double a, double b) { x = a; y = b; }
// ...
}

// File: paquete2/Segmento.java
package paquete2;
import paquete1.*; // importación de todas las clases del paquete paquete1
import paquete1.Punto; // importación explícita de la clase Punto de paquete1
public class Segmento {
private Punto origen, extremo; // utilización importada de Punto
public Segmento(double x1, double y1, double x2, double y2) {
origen = new Punto(x1, y1); // utilización importada de Punto
extremo = new Punto(x2, y2); // utilización importada de Punto
}
// ...
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 11 / 104
Paquetes básicos de Java

java.lang: para funciones del lenguaje.


java.util: para utilidades adicionales.
java.io: para entrada y salida.
java.text: para formato especializado.
java.awt: para diseño gráfico e interfaz de usuario.
java.awt.event: para gestionar eventos.
javax.swing: nuevo diseño de GUI.
java.net: para comunicaciones.
...

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 12 / 104
Acceso a las bibliotecas de Java
Todas las clases del paquete java.lang se importan automáticamente a
cualquier programa de Java, por lo que no es necesario ni cualificarlas ni
importarlas explícitamente. Por ejemplo String, System o Math.
Para todas las demás clases del resto de bibliotecas, sí es necesario cualificar
o importar explícitamente el paquete al que pertenece.
Por ejemplo, el siguiente programa calcula el valor medio de un millón de
números generados aleatoriamente, usando la clase Random del paquete
java.util y las clases String y System del paquete java.lang.
import java.util.*; // importa todas las clases de java.util
import java.util.Random; // importa la clase Random de java.util
public class TestAleatorio {
public static void main(String[] args) {
// java.util.Random rnd = new java.util.Random(); // cualificación explícita
Random rnd = new Random(); // utilización implícita
double sum = 0.0;
for (int i = 0; i < 1000000; ++i) {
sum += rnd.nextDouble();
}
System.out.println("media = " + sum / 1000000.0); // utilización implícita
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 13 / 104
Acceso a paquetes

Los paquetes del sistema cuelgan de varios subdirectorios específicos:


<system>/java y <system>/javax
Cuando una clase importa un determinado paquete o clase, el compilador lo
busca por defecto entre los paquetes del sistema y, además, en el
directorio raiz del proyecto Java al que pertenece la clase.
Para que el compilador busque paquetes en otro sitio, se debe especificar en la
variable CLASSPATH del entorno.
La variable CLASSPATH del entorno contiene una lista con todos directorios de
búsqueda de los paquetes.
El nombre de cada paquete debe coincidir con la ruta que va desde algún
directorio del CLASSPATH (o desde /java o /javax) al subdirectorio
correspondiente donde reside el paquete. Por ejemplo: java.util y
java.awt.event

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 14 / 104
Jerarquía de paquetes

Frontera del CLASSPATH

javax
java

util lang

io

Otros Paquetes java.util java.lang


java.io
Paquetes del Sistema

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 15 / 104
Fichero Java

Cada clase declarada como pública debe de estar en un fichero .java con su
mismo nombre.
Cada fichero .java puede contener varias clases e interfaces pero sólo una
podrá ser pública, el resto tendrá visibilidad dentro del propio paquete.
En caso de que la clase pertenezca a un determinado paquete, entonces el
fichero residirá en la jerarquía de directorios (carpetas) especificada por la
ruta del nombre del paquete.
Cada fichero .java debe compilarse, generando un fichero .class (en
bytecodes) por cada clase contenida en él.
El programa se ejecuta pasando el fichero .class de la clase distinguida al
intérprete de la Máquina Virtual de Java.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 16 / 104
Control de Acceso y Visibilidad
Existen cuatro niveles de acceso y visibilidad:
private - acceso privado, sólo desde dentro de la propia clase.
Por omisión - acceso desde dentro del propio paquete (package).
protected - acceso protegido, desde dentro del paquete y de las clases
herederas (subclases).
public - acceso público, desde cualquier sitio.

Nivel de Acceso

Desde Desde Desde Desde


Propia Propio Una Otra
Clase Paquete Subclase Clase

□ - private SÍ NO NO NO

▵▴ ~ package SÍ SÍ NO NO

⋄ ⬩ # protected SÍ SÍ SÍ NO

◦ • + public SÍ SÍ SÍ SÍ

Las clases e interfaces de nivel externo sólo pueden tener visibilidad pública o paquete.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 17 / 104
Símbolos en Eclipse para Diagramas de Clases UML

A
C Clase C ClaseAbstracta E Enumerado
S F
varInstanciaPrivada: int C
ClaseAbstracta() Rojo: Enumerado
S F
varInstanciaProtegida: int metodoInstanciaPublico(): int Verde: Enumerado
S F
varInstanciaPaquete: int A
metodoAbstractoPublico(): int Azul: Enumerado
varInstanciaPublica: int S
S
varClasePrivada: int values(): Enumerado[]
S
S F
CONST_CLASE_PRIVADA: int valueOf(String): Enumerado
ordinal(): int
C
Clase() toString(): String
metodoInstanciaPrivado(): int hashCode(): int
metodoInstanciaProtegido(): int I Interfaz equals(Object): boolean
metodoInstanciaPaquete(): int S F
CONST_CLASE_PUBLICA: int compareTo(Enumerado): int
metodoInstanciaPublico(): int
S A
metodoClasePrivado(): int metodoAbstractoPublico(): int

C SuperClase «interface» «interface»


I Interfaz I Interfaz

extends implements extends

C SubClase obj C Clase obj «interface»


I Interfaz
0.. 0..
* *

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 18 / 104
Instrucciones/sentencias
Existen tres tipos de instrucciones o sentencias, que se pueden utilizar en la
implementación de los métodos de las clases:
Sentencias de declaración de variables locales.
Sentencias de control de ejecución.
Secuencia.
Selección.
Iteración (repetición).
Control de Excepciones.

Sentencias de expresión:
Asignaciones, Incrementos y decrementos.
Creaciones de objetos.
Invocaciones a métodos (Mensajes).

Un bloque es un grupo de cero o más sentencias entre llaves { ... }, dando


lugar a una sentencia compuesta.
Un bloque se puede usar en cualquier parte donde se pueda utilizar una
sentencia simple.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 19 / 104
Sentencias de selección

if ( <exp_lógica> ) { switch (<exp>) { // char byte short


/* <sentencias> */ case <valor_1> : // int String
} // <sentencias>
break;
if ( <exp_lógica> ) { case <valor_2> :
/* <sentencias> */ // <sentencias>
} else { break;
/* <sentencias> */ ...
} case <valor_j> :
case <valor_k> :
if ( <exp_lógica> ) { // <sentencias>
/* <sentencias> */ break;
} else if ( <exp_lógica> ) { default :
/* <sentencias> */ // <sentencias>
} else { break;
/* <sentencias> */ }
}

En el caso del switch con una expresión de tipo String, la comparación con
los valores de los case se realiza utilizando el metodo equals().

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 20 / 104
Sentencias de iteración (repetición)

while ( <exp_lógica> ) {
// <sentencias>
}

do {
// <sentencias>
} while ( <exp_lógica> );

for ( <exp_ini> ; <exp_lógica> ; <exp_incr> ) {


// <sentencias>
}

for ( <tipo_elemento> <vble> : <array_o_colección_de_tipo_elemento> ) {


// <sentencias>
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 21 / 104
Criterios de codificación y corrección

Sólo están permitidas las sentencias y estructuras de selección e iteración que


aparecen en los apuntes y que serán vistas en clase (if, switch, while,
do-while, for, etc.). No se podrán usar otras como goto, continue, etc. La
sentencia break sólo se podrá utilizar en la estructura switch.
No se puede modificar la variable de control de un bucle for dentro de su
cuerpo. El número de iteraciones que realiza el bucle for debe quedar
claramente especificado en la cabecera del mismo.
En una función, sólo se utilizará una única sentencia return, y será la última
sentencia del cuerpo de dicha función. En un procedimiento, no se utilizará
ninguna sentencia return.
Estos criterios de codificación serán considerados en la corrección del código
proporcionado por el alumno.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 22 / 104
Expresiones

Una expresión es una combinación de los siguientes elementos, combinados


adecuadamente según la sintaxis del lenguaje:
Valores literales.
Variables.
Operadores.
Invocaciones a métodos (Mensajes).

Una expresión se evalúa a:


Un valor de tipo primitivo (boolean, char, int, double, etc).
Una referencia a un objeto.
Una referencia a un array.

La evaluación de una expresión devuelve el resultado calculado.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 23 / 104
Operadores
Un operador es una función de uno, dos o tres argumentos (operandos).
Aritméticos: (unarios) +, -, ++, -- y (binarios) +, -, *, /, %
Relacionales/comparación (binarios): ==, !=, <, <=, >, >=
Lógicos: (unario) !, (binarios) &&, || (evaluación en CORTO-CIRCUITO)
Manipulación de bits: (unario) ~, (binarios) &, |, ˆ, <<, >>, >>>
Otros operadores: (unario) new, (binario) instanceof, (ternario) ?:
Asignación (binarios, requieren una variable a la izquierda):
=, +=, -=, *=, /=, %=, &=, |=, ˆ=

Con un operador y sus operandos se construyen expresiones simples.


3 * 5 x + 7.3 'a' <= 45

Las expresiones simples se combinan dando lugar a expresiones compuestas.


3 + 5 * x / 7.3 y * (x + 7.3) (x > y) ? x : y

El orden de evaluación de las expresiones compuestas depende de la


precedencia y de la asociatividad de los operadores que aparezcan en la
expresión.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 24 / 104
Precedencia y asociatividad de operadores

Precedencia (de mayor a menor) Asociatividad


paréntesis (x) NO
acceso e incr x[i] x.y x++ x-- Izquierda
unarios ++x --x +x -x !x ~x Derecha
creación y cast new T() (T)x Derecha
multiplicativos * /% Izquierda
sumatorios +- Izquierda
desplaz-bits << >> >>> Izquierda
relacionales < <= > >= instanceof Izquierda
igualdad == != Izquierda
y-bits & Izquierda
xor-bits ˆ Izquierda
o-bits | Izquierda
y-lógico && Izquierda
o-lógico || Izquierda
condicional b?x:y Derecha
asignación = += -= *= /= %= &= |= ˆ= <<= >>= >>>= Derecha

Evaluación en CORTO-CIRCUITO de los operadores lógicos && ||

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 25 / 104
Conversiones implícitas de tipos y clases (automáticas)

Conversiones implícitas (automáticas)


Conversiones automáticas de tipos primitivos a tipos más amplios:
byte ▸ short ▸ int ▸ long ▸ float ▸ double
char
En caso de polimorfismo, conversiones automáticas desde subclases a
superclases, en la línea jerárquica de herencia.
Las conversiones automáticas se aplican en los siguientes contextos:
Asignaciones: el tipo del valor de la expresión promociona al tipo de la variable
destino. Ej.: double x = 3 * 4; Coche c = new CocheColor("Rojo");
Evaluación de expresiones aritméticas: los tipos de los operandos
promocionan al tipo mas amplio de los operandos (como mínimo se
promocionan a int). Ej.: double x = 3 * 4.5;
Invocaciones a métodos: los tipos de los parámetros actuales promocionan a
los tipos de los parámetros formales. Ej.: double x = Math.sqrt(4 * 4);
Concatenación de cadenas: los valores de los operandos se convierten en
String automáticamente (en el caso de objetos se invoca automáticamente al
método toString()). Ej.: String x = "Pi = " + 3.1416;

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 26 / 104
Conversiones explícitas de tipos y clases (casting)

Conversiones explícitas (casting)


Las conversiones de tipo explícitas (casting) se realizan mediante la siguiente
construcción (se comprueban durante la ejecución):

( <tipo/clase> ) <expresión> ( <tipo/clase> ) ( <expresión> )

Ejemplos
int x1 = (int) 3.7 * 2; // x1 = 6
int x2 = (int) (3.7 * 2); // x1 = 7
double x3 = (double) 1 / 2; // x2 = 0.5
double x4 = (double) ( 1 / 2 ); // x3 = 0.0

Coche c1 = new CocheColor("Rojo");


if (c1 instanceof CocheColor) {
CocheColor c3 = (CocheColor) c1;
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 27 / 104
Control de excepciones (I)

Las excepciones son un mecanismo de ayuda para la comunicación y el


manejo de errores.
Cuando se produce un error en un método:
1 Se crea un objeto de la clase Exception (de java.lang) o derivada, con
información sobre el error.
2 Se lanza el objeto excepción creado anteriormente (el sistema o el programador
mediante la instrucción throw).
3 Se interrumpe el flujo normal de ejecución.
4 El entorno de ejecución intenta encontrar un manejador para dicho objeto
excepción.
1 Dentro del propio método
2 En un método anterior en la pila de activaciones.
3 Si no se encuentra un manejador para esa excepción, entonces se aborta la
ejecución del programa.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 28 / 104
Control de excepciones (II)
Existen cuatro sentencias relacionadas con el control de excepciones:
throw: lanza un objeto excepción con información sobre el error producido.
try: delimita un bloque de código donde, en caso de que se lance una
excepción, ésta podría ser capturada y manejada.
catch: delimita un bloque de código asociado a un bloque try donde se
capturan y manejan algunos tipos de excepciones determinados.
finally: delimita un bloque de código que se ejecutará siempre que se
ejecute el bloque try correspondiente, tanto si se producen excepciones como
si no.
try {
// <sentencias> // Bloque vigilado // throw
} catch ( <tipo_excepción> <vble> ) {
// <sentencias> // Manejador
} catch ( <tipo_excepción> <vble> ) {
// <sentencias> // Manejador
} finally {
// <sentencias> // Siempre se ejecuta
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 29 / 104
Tipos y variables

Tipos de datos primitivos

Tipo Valores Rango de Valores Ejemplos


▸ boolean lógicos false y true false y true
▸ char Unicode de 16 bits Unicode UTF-16 'a', '$', '\t', '\n', '\u00F1'
byte enteros de 8 bits ±127 100, -34
short enteros de 16 bits ±32767 2578, -93
▸ int enteros de 32 bits ±2147483647 56, 0xaf, 0xAF, 0b1001, 1_000
long enteros de 64 bits ±9223372036854775807 8456L, 33456L
float reales de 32 bits ±3.40282E±38 67.345f, 34.122F, 21.34e2f
▸ double reales de 64 bits ±1.79769313E±308 4.66, 23.7e3, 35.213d, 23.2D

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 30 / 104
Tipos y variables

Valores de tipos de datos primitivos


Cada tipo primitivo define un rango de valores que permite representar y
manipular la información, en forma de datos.
Los valores se pueden almacenar y manipular mediante variables.
Además, los valores se pueden manipular directamente, usando sus
representaciones literales.

Variables de tipos de datos primitivos


Las variables de tipos de datos primitivos almacenan, en un momento dado, un
determinado valor de entre los valores posibles definidos por el tipo.
cnt letra pi ok int cnt = 1;
char letra = 'a';
1 'a' 3.14 true double pi = 3.14;
boolean ok = true;
La asignación (=) modifica el valor almacenado en una variable.
Los operadores (==, !=, <, <=, >, >=) comparan los valores de las variables
de tipos primitivos.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 31 / 104
Tipos y variables
Clases
Una Clase representa una abstracción de datos, especifica las características de
unos objetos: su estado interno (atributos) y su comportamiento (métodos).

Variables de referencia a objetos


Las variables de una determinada Clase no almacenan un objeto de esa Clase,
sino que almacenan una referencia polimórfica a un objeto que haya sido
creado dinámicamente, o null.
pto1 Punto pto2 pto3 Punto pto4 Punto pto1 = new Punto(1,2);
Punto pto2 = pto1;
• ▸ 1 2 ◂ • • ▸ 3 4 / Punto pto3 = new Punto(3,4);
Punto pto4 = null;
La asignación (=) asigna la referencia (al mismo objeto compartido).
Los operadores (==, !=) comparan las referencias, es decir, si ambas
variables referencian al mismo objeto.
Para comparar los contenidos de los objetos se debe invocar al método equals:
pto1.equals(pto3).

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 32 / 104
Tipos y variables
Referencias a Arrays
Se pueden definir arrays de tipos primitivos, de referencias a objetos y multi-dimensionales.

Variables de referencia a arrays


Las variables de tipo array no almacenan el propio array, sino que almacenan
una referencia a un array que haya sido creado dinámicamente, o null.
int[] elms = new int[4];
int[][] mat = new int[2][3];
Punto[] ptos = new Punto[4];
int[] datos = null;

elms • ▸ 0 0 0 0 ptos • ▸ / / / / datos /

▸ 0 0 0
mat • ▸ •

• ▸ 0 0 0

La asignación (=) asigna la referencia (al mismo array compartido).


Los operadores (==, !=) comparan las referencias, no los contenidos.
Los elementos se inicializan automáticamente con los valores por defecto.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 33 / 104
Tipos y variables
Referencias a Arrays
Se pueden definir arrays de tipos primitivos, de referencias a objetos y multi-dimensionales.

Variables de referencia a arrays


Las variables de tipo array no almacenan el propio array, sino que almacenan
una referencia a un array que haya sido creado dinámicamente, o null.
int[] elms = new int[] { 1, 2, 3, 4 };
int[][] mat = new int[][] { { 3, 4, 5 }, { 6, 7, 8 } };
Punto[] ptos = new Punto[] { new Punto(1,2), null, null, new Punto(3,4) };
int[] datos = null;

elms • ▸ 1 2 3 4 ptos • ▸ • / / • datos /

▸ 3 4 5 ▾ ▾
mat • ▸ • Punto Punto

• ▸ 6 7 8 1 2 3 4

La asignación (=) asigna la referencia (al mismo array compartido).


Los operadores (==, !=) comparan las referencias, no los contenidos.
Los elementos se inicializan automáticamente con los valores por defecto.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 34 / 104
Tipos y variables
Referencias a Arrays
Se pueden definir arrays de tipos primitivos, de referencias a objetos y multi-dimensionales.

Variables de referencia a arrays


Las variables de tipo array no almacenan el propio array, sino que almacenan
una referencia a un array que haya sido creado dinámicamente, o null.
int[] elms = { 1, 2, 3, 4 };
int[][] mat = { { 3, 4, 5 }, { 6, 7, 8 } };
Punto[] ptos = { new Punto(1,2), null, null, new Punto(3,4) };
int[] datos = null;

elms • ▸ 1 2 3 4 ptos • ▸ • / / • datos /

▸ 3 4 5 ▾ ▾
mat • ▸ • Punto Punto

• ▸ 6 7 8 1 2 3 4

La asignación (=) asigna la referencia (al mismo array compartido).


Los operadores (==, !=) comparan las referencias, no los contenidos.
Los elementos se inicializan automáticamente con los valores por defecto.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 35 / 104
Ámbito de una variable

El ámbito de una variable es la zona de código donde se puede usar su


identificador sin calificar.
Un identificador debe ser único dentro de su ámbito.
El ámbito determina cuándo se crea y cuándo se destruye el espacio de
memoria para la variable.
Las variables, según su ámbito, se clasifican en las siguientes categorías:
Variable de clase o de instancia (declarada dentro de una clase).
Variable local (declarada dentro de un método).
Parámetro de método (declarada en la lista de parámetros de un método).
Parámetro de gestor de excepciones (declarada dentro de catch (...)).

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 36 / 104
Inicialización de variables

Cuando no se le asigna un valor explícitamente a una variable:


Las variables de clase (no para final) se inicializan automáticamente al cargar
la clase.
Las variables de instancia (no para final) se inicializan automáticamente cada
vez que se crea una instancia.
Las variables locales no se inicializan de forma automática, tienen inicialmente
un valor basura y el compilador produce un error si se utilizan sin haber sido
asignado un valor.
Los elementos de un array se inicializan automáticamente cuando se crea el
array.

Valores de inicialización automática para cada tipo:


boolean: false // boolean
char: '\u0000' // char
int: 0 // byte, short, int y long
double: +0.0 // float y double
Object: null // referencia a un objeto de cualquier tipo
Array[]: null // referencia a un array de cualquier tipo

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 37 / 104
Identificadores
Los identificadores dan nombre a: variables, métodos, clases e interfaces.
Un identificador (nombre) es una secuencia arbitraria de caracteres Unicode:
letras, dígitos, subrayado o símbolos de monedas. No debe comenzar por
dígito ni coincidir con alguna palabra reservada.
int numero;

Por convenio:
Nombres de variables y métodos en minúsculas. Si son compuestos, las
palabras no se separan y comienzan con mayúscula.
long valorMaximo;

Nombres de clases e interfaces comienzan con mayúscula, seguido de


minúsculas. Si son compuestos, las palabras no se separan y comienzan con
mayúscula.
class NumeroRacional { ... }

Nombres de constantes todo en mayúsculas. Si son compuestos, las palabras se


separan con subrayados.
final double CTE_GRAVITACION = 6.67408e-11;
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 38 / 104
Clases en Java
Una clase pública debe estar definida en un fichero .java con su mismo
nombre.
La definición de una clase consta de los siguientes elementos:
Especificación del paquete al que pertenece la clase. Si no se especifica,
entonces pertenece al paquete por defecto (anónimo).
Sentencias de importación de clases y paquetes.
Especificación del nombre de la clase, de la relación de herencia e
implementación de interfaces.
Especificación de los atributos, tanto variables de instancia como variables de
clase, especificando su nombre, tipo, y cualificadores necesarios (static,
final), así como de su nivel de visibilidad (public, protected y private).
Definición de los constructores, diferenciados por los parámetros que reciben,
especificando su nivel de visibilidad (public, protected y private).
Definición de los métodos de instancia y de los métodos de clase,
especificando su nombre, tipo, parámetros, y cualificadores necesarios (static,
final), así como de su nivel de visibilidad (public, protected y private).
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 39 / 104
Ejemplo: Clase Punto

Abstracción: Punto del plano Cartesiano


Un punto representa una determinada posición en el plano Cartesiano.
Comportamiento de un punto:
Especificar el valor de sus coordenadas X e Y.
Consultar el valor de sus coordenadas X e Y.
Calcular la distancia que lo separa de otro objeto punto.
Desplazar según una distancia especificada en ambos ejes.
Estado interno del punto:
El valor de la coordenada X (abscisa).
El valor de la coordenada Y (ordenada).
Podemos crear múltiples objetos de la Clase Punto:
Punto(1,2), Punto(2,1), Punto(3,3), Punto(4,1)
(3,3)

(1,2)

(2,1) (4,1)
• •

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 40 / 104
Ejemplo: Clase Punto
package geometria;
public class Punto { // fichero Punto.java
private double x, y; // Atributos, variables de instancia
public Punto() {
this(0, 0); // invoca al siguiente constructor segun parámetros // x = 0; y = 0;
}
public Punto(double a, double b) {
x = a;
y = b;
}
public double getAbscisa() {
return x;
}
public double getOrdenada() {
return y;
}
public void setAbscisa(double a) {
x = a;
}
public void setOrdenada(double b) {
y = b;
}
public void desplazar(double a, double b) {
x += a;
y += b;
}
public double distancia(Punto pto) {
return Math.sqrt(Math.pow(this.x - pto.x, 2) + Math.pow(this.y - pto.y, 2));
}
} Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Dpto. Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 41 / 104
Ejemplo: Clase Segmento (Composición)

Abstracción: Segmento del plano Cartesiano


Un segmento es un fragmento de una recta que está comprendido entre dos puntos
en el plano Cartesiano.
Comportamiento de un segmento:
Especificar los puntos que delimitan el segmento.
Especificar el valor de las coordenadas X e Y de ambos puntos del segmento.
Calcular la longitud del segmento.
Desplazar el segmento según una distancia especificada en ambos ejes.
Estado interno del segmento:
Los dos puntos que delimitan el segmento.
Podemos crear múltiples objetos de la Clase Segmento:
Segmento(2, 1, 3, 3), Segmento(Punto(6,3), Punto(7,1))

• (3,3) • (6,3)
 
 
 
• (2,1) • (7,1)

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 42 / 104
Ejemplo: Clase Segmento (Composición)

package geometria;
public class Segmento { // fichero Segmento.java
private Punto extremo1, extremo2; // Atributos, variables de instancia
//public Segmento(double x1, double y1, double x2, double y2) {
// extremo1 = new Punto(x1, y1);
// extremo2 = new Punto(x2, y2);
//}
public Segmento(double x1, double y1, double x2, double y2) {
this( new Punto(x1, y1), new Punto(x2, y2) ); // invoca al siguiente constructor
}
public Segmento(Punto p1, Punto p2) {
extremo1 = p1;
extremo2 = p2;
}
public void desplazar(double a, double b) {
extremo1.desplazar(a, b); // invocación a métodos de la clase Punto
extremo2.desplazar(a, b); // invocación a métodos de la clase Punto
}
public double longitud() {
return extremo1.distancia(extremo2); // invocación a métodos de la clase Punto
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 43 / 104
Variables de instancia
Las variables de instancia se definen especificando el nivel de visibilidad, el tipo y el
nombre. Además, se puede especificar el cualificador final en caso de ser necesario,
así como también el valor con el que será inicializada.
Las variables de instancia estan asociadas a cada objeto. Cada objeto tiene sus
propias variables de instancia independientes.
Se crean cuando se crea dinámicamente el objeto al que pertenecen.
Se destruyen cuando se destruye el objeto al que pertenecen.
Ej. cada punto tiene dos variables de instancia : x, y

public class Punto {


pto1 Punto pto2 Punto
private double x, y; // x e y son variables
• ▸ 1 2 • ▸ 2 1 // ... // de instancia
}

Las variables de instancia se acceden cualificándolas con el nombre de la referencia


al objeto al que pertenecen (this para el objeto implicado, aunque se puede suprimir
si no hay conflicto de nombres). Por ejemplo: pto.x, this.x, x.
Se pueden declarar final si su valor no cambiará (será constante).
Se inicializan con un valor por defecto (cero o null) si no se especifica ningún otro
valor (no para final).
Desde fuera de la clase, hay que tener en cuenta el nivel de visibilidad.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 44 / 104
Definición de constructores de objetos
Se define un constructor de una clase especificando el nivel de visibilidad, el
nombre de la clase, seguido por la lista de parámetros, y por el cuerpo que
especifica las sentencias necesarias para construir un objeto adecuadamente.
En la definición de una clase se pueden definir varios constructores: con distinto
número de argumentos o con argumentos de distintos tipos.
Si no se define ningún constructor explícitamente, entonces el sistema proporciona
automáticamente un constructor por defecto, sin parámetros, que asigna valores
iniciales por defecto a las variables de instancia del objeto creado.
Un constructor sólo puede invocar a métodos private, final o static, ya que los
métodos public y protected podrían ser redefinidos por las subclases (cuyos
atributos no estarían construidos).
Un constructor puede invocar a otro constructor de la misma clase especificando en
la primera línea del cuerpo al objeto this seguido por la lista de parámetros
adecuados.

public class Punto { public Punto(double a, double b) {


private double x, y; x = a;
public Punto() { y = b;
this(0, 0); }
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 45 / 104
Métodos de instancia
Los métodos de instancia se definen especificando el nivel de visibilidad, el tipo del
valor devuelto, el nombre del método, la lista de parámetros, seguida por el cuerpo,
que especifica las sentencias necesarias según el comportamiento del método.
Además, se puede especificar el cualificador final en caso de ser necesario
Los métodos de instancia se invocan cualificándolos con el nombre de la referencia
al objeto sobre el que se aplican (this para el objeto implicado, aunque se puede
suprimir si no hay conflicto de nombres). Por ejemplo: p1.distancia(p2),
this.distancia(part), distancia(part).
Pueden acceder directamente tanto a las variables de clase como a las variables de
instancia del propio objeto implicado. Pueden invocar directamente tanto a los
métodos de clase como a los métodos de instancia sobre el propio objeto.
Desde fuera de la clase, hay que tener en cuenta el nivel de visibilidad.
public class Punto {
private double x, y;
public double distancia(Punto pto) {
return Math.sqrt(Math.pow(this.x - pto.x, 2) + Math.pow(this.y - pto.y, 2));
}
}
public class Segmento {
private Punto origen, extremo;
public double longitud() {
return origen.distancia(extremo);
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 46 / 104
Paso de Parámetros (Argumentos) (I)
Los parámetros (también denominados argumentos) se declaran en la
definición de los constructores y de los métodos.
Hay una instancia independiente por cada invocación al método.
Se crean cuando se ejecuta la invocación a un determinado método.
Se destruyen cuando termina la ejecución del método invocado.
Se inicializan como una copia de los valores especificados en la invocación al
método.
En Java, todos los parámetros son por valor. No existe el paso por referencia.
public class Punto {
private double x, y; // x e y son variables de instancia
public void desplazar(double a, double b) {
x += a; // a y b son parámetros
y += b;
}
}
public static void main(String[] args) {
Punto p1 = new Punto(3, 4);
p1.desplazar(2, 6);
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 47 / 104
Paso de Parámetros (Argumentos) (II)

El paso de parámetros en Java es Por Valor, esto es, se realiza una copia del
valor del parámetro real en el parámetro formal correspondiente. No existe el
paso por referencia.
El paso de parámetros de tipos primitivos implica una copia independiente
del valor almacenado.
Cualquier modificación en el parámetro formal dentro del método no afecta al
valor almacenado en el parámetro actual.
El paso de parámetros de objetos implica una copia de la referencia, en
cuyo caso el mismo objeto referenciado es compartido entre el método
invocante y el invocado.
Cualquier modificación en el objeto referenciado por el parámetro formal dentro
del método sí afecta al estado del objeto referenciado por el parámetro actual.

De igual modo sucede en el caso de los arrays.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 48 / 104
Variables Locales

Las variables locales se declaran dentro del cuerpo de los constructores, y de


los métodos.
Hay una instancia independiente por cada invocación al método.
Se crean cuando se ejecuta la instrucción de declaración de la variable.
Se destruyen cuando termina la ejecución del ámbito del bloque donde fue
declarada.
Si no se inicializa, la variable contiene un valor inespecificado (basura).
public class Poligono {
// ...
public double perimetro() {
double suma = 0; // suma e i son variables locales
for (int i = 0; i < ptos.length - 1; ++i) {
suma += ptos[i].distancia(ptos[i+1]);
}
return suma;
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 49 / 104
Ejemplo: la clase NumeroRacional
Defina la clase NumeroRacional que represente los números racionales.
Estado interno de los objetos: almacenará el numerador y el denominador.
Proporcionará los siguientes constructores y métodos públicos:
Ctor. por defecto, crea el numero racional 0/1.
Ctor(x,y), crea el numero racional x/y normalizado.
Consulta del estado interno del objeto (numerador y denominador).
Sumar, Restar, Multiplicar y Dividir, reciben como parámetro un número
racional y devuelven un nuevo número racional resultado de aplicar la operación
al número racional actual con el número racional recibido como parámetro.
Representación textual del objeto (toString()).

Un número racional normalizado:


Atención al caso del denominador cero (0).
Atención al caso del numerador cero (0).
El denominador siempre debe ser positivo.
La fracción siempre se almacena en modo reducido. Es necesario calcular el MCD.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 50 / 104
Variables de clase
Las variables de clase se definen especificando el nivel de visibilidad, el cualificador
static, el tipo, el nombre, y el valor con el que será inicializada. Además, se puede
especificar el cualificador final en caso de ser necesario.
Las variables de clase estan asociadas a la clase.
Existen, aunque no se hayan creado objetos de la clase.
Sólo hay una única instancia, común y compartida por todos los objetos de la
misma clase.
Se acceden cualificándolas con el nombre de la clase a la que pertenecen. Por
ejemplo: Particula.G.
Dentro de la propia clase, se acceden directamente, sin necesidad de cualificación (se
puede utilizar this si es necesario). Por ejemplo: G, this.G.
Se pueden declarar final si su valor no cambiará (será constante).
Se deben inicializar en la declaración de la variable. Se inicializan con un valor cero
o null si no se especifica ningún otro valor (no para final).
Desde fuera de la clase, hay que tener en cuenta el nivel de visibilidad.
public class Particula extends Punto {
private static final double G = 6.67408e-11; // variable de clase constante
// ...
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 51 / 104
Métodos de clase
Los métodos de clase se definen especificando el nivel de visibilidad, el cualificador
static, el tipo del valor devuelto, el nombre del método, la lista de parámetros,
seguida por el cuerpo, que especifica las sentencias necesarias según el
comportamiento del método.
Los métodos de clase estan asociados a la clase.
Existen, aunque no se hayan creado objetos de la clase.
Se invocan cualificándolos con el nombre de la clase a la que pertenecen. Por
ejemplo: Math.sqrt(x), Math.pow(x, 2).
Dentro de la propia clase, se invocan directamente, sin necesidad de cualificación (se
puede utilizar el nombre de la clase, o this si es necesario).
Sólo pueden acceder directamente a las variables de clase.
Sólo pueden invocar directamente a los métodos de clase.
Desde fuera de la clase, hay que tener en cuenta el nivel de visibilidad.
public class NumeroRacional {
private static int mcd(int n, int m) {
n = Math.abs(n); m = Math.abs(m);
while (m != 0) {
int r = n % m;
n = m;
m = r;
}
return n;
Dpto. }
Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 52 / 104
Ejemplo

sqrt() y pow() son métodos de clase de la clase Math y se invocan, en la


clase Punto, cualificándolos con el nombre de la clase Math.
public double distancia(Punto pto) {
// Invocación a métodos estáticos
return Math.sqrt(Math.pow(this.x - pto.x, 2)
+ Math.pow(this.y - pto.y, 2));
}

out es una variable de clase y currentTimeMillis() es un método de


clase, ambos públicos de la clase System:
public class Ejemplo {
public static void main(String[] args) {
// Acceso a variable estática
System.out.println("Hola");
// Invocación a método estático
long time = System.currentTimeMillis();
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 53 / 104
Métodos de clase factorías
A veces, para construir adecuadamente un objeto, además de invocar al constructor
de la clase con el operador new, se requiere realizar acciones adicionales.
En estas circunstancias puede ser adecuado la definición de métodos de clase
factorías, los cuales se encargan de construir adecuadamente un objeto, realizando
las acciones que sean necesarias para ello, devolviendo como resultado una referencia
al nuevo objeto creado.
public class Punto {
private double x, y;
public Punto() { this(0, 0); }
public Punto(double a, double b) { x = a; y = b; }
public double getAbscisa() { return x; }
public double getOrdenada() { return y; }
public static Punto crearPuntoMedio(Punto[] pts) { // método de clase FACTORÍA
double sx = 0; // recibe un array de puntos,
double sy = 0; // calcula el punto medio,
if (pts.length > 0) { // lo crea y lo devuelve
for(int i = 0; i < pts.length; ++i) {
sx += pts[i].getAbscisa();
sy += pts[i].getOrdenada();
}
sx = sx / pts.length;
sy = sy / pts.length;
}
return new Punto(sx, sy);
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 54 / 104
Creación de objetos
Cada instancia (objeto) se crea dinámicamente invocando, mediante el
operador new, al constructor de la clase, especificando la lista de argumentos
adecuada. A veces, de forma indirecta a través de métodos de clase factorías.
El operador new reserva el espacio de memoria adecuado para almacenar el
estado interno del nuevo objeto a crear.
El constructor asigna unos valores iniciales a sus variables de instancia.
El operador new devuelve una referencia al objeto que crea, que puede ser
asignado a una variable, o puede ser utilizado directamente en una expresión.
// Main.java
public class Main {
public static void main(String[] args) {
Punto pto1 = new Punto(1, 2);
Punto pto2 = new Punto(2, 1);
double d = new Punto(3,4).distancia(new Punto(4,5));
Punto pto3 = Punto.crearPuntoMedio(new Punto[] { pto1, pto2 } );
}
}

pto1 Punto pto2 Punto

• ▸ 1 2 • ▸ 2 1

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 55 / 104
La vida de los objetos
Los objetos son siempre instancias de alguna clase.
Durante la ejecución de un programa:
Se crean objetos con el operador new.
Los objetos no necesarios se eliminan automáticamente, cuando se pierden las
referencias a dichos objetos (recolección de basura automática).
Anular la referencia a los objetos no utilizados (variable = null) ayuda a la
eliminación y recolección de los objetos que ya no son necesarios.
Se puede invocar al recolector de basura (System.gc()) para la destrucción de
los objetos y recuperar la memoria, aunque se suele invocar de forma automática.

Los objetos se pueden manipular, e interactúan entre sí invocando a métodos


aplicados sobre los objetos, así como pasándolos como parámetros en la
invocación a métodos.
public class Main {
public static void main(String[] args) {
Punto pto1 = new Punto(1, 2);
Punto pto2 = new Punto(2, 1);
pto2.desplazar(4, 5);
double d = pto1.distancia(pto2);
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 56 / 104
Ejemplo: la clase Coche

La clase Coche representa información sobre las características de un coche.


Cada objeto coche está determinado por su número de referencia, el modelo y
su precio base.
Además, todos los objetos de la clase comparten los mismos gastos de
matriculación (fijo 100€) y el IVA (inicialmente 10 %).
Proporcionará los siguientes constructores y métodos públicos:
Ctor. a partir del modelo y su precio base. El número de referencia se asigna
automáticamente de manera consecutiva.
Consultar el estado interno del objeto (referencia y modelo) y el IVA que se
aplica.
Las subclases podrán consultar el precio base del estado interno del objeto.
Modificar tanto el precio base como el IVA a aplicar.
Calcular el precio final del coche (gastos de matriculación más el precio base más
el resultado de aplicar el porcentaje de IVA).
Obtener la representación textual del objeto (toString()).

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 57 / 104
Ejemplo: la clase Coche
public class Coche {
private static final double GASTOS_MATR = 100.0; // Constante de Clase
private static double Iva = 10.0; // Variable de Clase
private static int refCnt = 1; // Variable de Clase
private final int referencia; // Constante de instancia
private final String modelo; // Constante de instancia
private double precio; // Variable de instancia
public Coche(String m, double p) { public int getRef() {
modelo = m; return referencia;
precio = p; }
referencia = refCnt; public String getModelo() {
++refCnt; return modelo;
} }
public double calcPrecioFinal() { protected double getPrecioBase() {
double p = GASTOS_MATR + getPrecioBase(); return precio;
return p + p * getIva() / 100.0; }
} public void setPrecioBase(double v) {
precio = v;
@Override }
public String toString() {
return "(" + getRef() + ", " + getModelo() + ", " + calcPrecioFinal() + ")";
}
public static double getIva() {
return Iva;
}
public static void setIva(double v) {
Iva = v;
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 58 / 104
Ejemplo: utilización de la clase Coche

Programa Principal Salida


public class Main { IVA: 10.0
public static void main(String[] args) { (1, Seat, 13310.0)
Coche c1 = new Coche("Seat", 12000); (2, Renault, 14410.0)
Coche c2 = new Coche("Renault", 13000); IVA: 20.0
System.out.println("IVA: " + Coche.getIva()); (1, Seat, 18120.0)
System.out.println(c1.toString()); (2, Renault, 15720.0)
System.out.println(c2.toString());
Coche.setIva(20);
c1.setPrecioBase(15000);
System.out.println("IVA: " + Coche.getIva());
System.out.println(c1);
System.out.println(c2);
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 59 / 104
Asignación o Copia
Las sentencias de asignación sobre variables de tipos primitivos permiten
almacenar una copia del valor en la variable.
Una variable que referencia a un objeto se puede asignar a otra variable de su
misma clase. En este caso se asigna la referencia al objeto, y ambas
variables referenciarán al mismo objeto compartido.
// Main.java
public class Main {
public static void main(String[] args) {
Punto pto1 = new Punto(1, 2);
Punto pto2 = pto1;
Punto pto3 = new Punto(1, 2);
int x = 3, y = 1;
y = x;
}
}

pto1 • ▸ Punto pto3 • ▸ Punto x 3

▸ 1 2 1 2

pto2 • y 3

Para duplicar (copiar) un objeto, se debe crear otro objeto de la


misma clase y duplicar (copiar) sus variables de estado.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 60 / 104
Ejemplo Segmento 1 (asignación)
Si desde un determinado objeto se referencia a objetos externos, entonces
esos objetos externos podrían ser accedidos y manipulados desde el exterior,
sin el control de la clase que los referencia.
public class Segmento {
private Punto origen, extremo;
public Segmento(Punto pto1, Punto pto2) {
origen = pto1; // Asignación (referencia a un objeto externo)
extremo = pto2; // Asignación (referencia a un objeto externo)
}
public double longitud() {
return origen.distancia(extremo);
}
public static void main(String[] args) {
Punto pt1 = new Punto(1, 3);
Punto pt2 = new Punto(2, 5);
Segmento sgt = new Segmento(pt1, pt2);
}
}

pt1 Punto Segment sgt

• ▸ 1 3 ◂ • • ◂ •

pt2 Punto

• ▸ 2 5 ◂

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 61 / 104
Ejemplo Segmento 2 (copia)
Si desde un determinado objeto se referencia a objetos internos, entonces esos
objetos internos no pueden ser manipulados desde el exterior, y se encuentran
bajo el control de la clase que los referencia.
public class Segmento {
private Punto origen, extremo;
public Segmento(Punto pto1, Punto pto2) {
origen = new Punto(pto1.getAbscisa(), pto1.getOrdenada()); // Copia (ref. obj. int
extremo = new Punto(pto2.getAbscisa(), pto2.getOrdenada()); // Copia (ref. obj. int
}
public double longitud() {
return origen.distancia(extremo);
}
public static void main(String[] args) {
Punto pt1 = new Punto(1, 3);
Punto pt2 = new Punto(2, 5);
Segmento sgt = new Segmento(pt1, pt2);
}
}

pt1 Punto sgt Segment Punto

• ▸ 1 3 • ▸ • • ▸ 1 3

Punto
pt2 Punto
▸ 2 5
• ▸ 2 5

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 62 / 104
Cadenas de caracteres
Las cadenas de caracteres se representan en Java como secuencias de
caracteres Unicode encerradas entre comillas dobles:
"Ejemplo de cadena de caracteres"

La clase String (de java.lang) permite representar y manipular cadenas de


caracteres. Dispone de constructores y métodos para crear y manipular Strings.
String str1 = new String("¡Hola!"); // Creación normal de Strings
String str2 = "¡Hola!"; // Creación simplificada de Strings
str2 = "¡Adios!"; // Asignación cambia la referencia a otro String

Los objetos de la clase String en Java son INMUTABLES. El objeto de la


clase String no se puede modificar, pero sí se puede cambiar la referencia de
una variable.
Los métodos para acceder a los caracteres de un objeto String:
length(): devuelve el número de caracteres de la cadena.
charAt(i): devuelve el carácter que se encuentra en la posición i en la cadena
(0 ≤ i < length()).
Si se intenta acceder a una posición no válida el sistema lanza una excepción:
IndexOutOfBoundsException.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 63 / 104
Cadenas de caracteres
La concatenación (+, +=) produce como resultado un nuevo objeto String
como resultado de unir dos cadenas de caracteres.
En la concatenación de cadenas de caracteres pueden intervenir otros tipos de
datos, que serán convertidos automáticamente a su representación String.
int i = 42;
System.out.println("i es " + i); // muestra: i es 42

En el caso de objetos:
Punto p = new Punto(3, 4);
System.out.println("p es " + p); // muestra: p es Punto@119c0982

Es necesario que la clase redefina el método público toString().


class Punto {
@Override
public String toString() {
return "(" + x + ", " + y + ")";
}
}
Punto p = new Punto(3, 4);
System.out.println("p es " + p); // muestra: p es (3, 4)
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 64 / 104
Cadenas de caracteres

Comparación de cadenas
c1.equals(c2): devuelve true si c1 y c2 son iguales y false en otro caso.
c1.equalsIgnoreCase(c2): igual que la anterior, pero sin tener en cuenta
las diferencias por mayúsculas y minúsculas.
c1.compareTo(c2): devuelve un entero menor, igual o mayor que cero
cuando c1 es menor, igual o mayor que c2.
c1.compareToIgnoreCase(c2): igual que la anterior, pero sin tener en
cuenta las diferencias por mayúsculas y minúsculas.
ATENCIÓN c1 == c2 compara las referencias, es decir, si ambas variables
referencian al mismo objeto.

String c1 = "pepe"; // c1 ref. a objeto con contenido "pepe"


String c2 = "peluca"; // c2 ref. a objeto con contenido "peluca"
String c3 = "pe"; // c3 ref. a objeto con contenido "pe"
c3 += "pe"; // c3 ref. a objeto con contenido "pepe"
boolean b1 = c1.equals(c2); // false (c1 y c2 ref. a objetos con contenido distinto)
boolean b2 = c1.equals(c3); // true (c1 y c3 ref. a objetos con el mismo contenido)
boolean b3 = c1 == c3; // false (c1 y c3 referencian a dos objetos distintos)
int r1 = c1.compareTo(c2); // > 0 ("pepe" es mayor que "peluca")

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 65 / 104
Cadenas de caracteres

Otros métodos
c1.indexOf(c2): devuelve la primera posición de c2 (carácter o cadena).
c1.lastIndexOf(c2): devuelve la última posición de c2 (carácter o cadena).
c1.toLowerCase(): devuelve un nuevo objeto String con todo minúsculas.
c1.toUpperCase(): devuelve un nuevo objeto String con todo mayúsculas.
c1.substring(desde, hasta): devuelve un nuevo objeto String con los
caracteres a partir de la posición desde y hasta la posición hasta (sin
incluirla).

String c1 = "Perro rojo";


int i1 = c1.indexOf("ro"); // 3
int i1 = c1.lastIndexOf("ro"); // 6
String c2 = c1.toLowerCase(); // "perro rojo"
String c3 = c1.toUpperCase(); // "PERRO ROJO"
String c4 = c1.substring(3, 8); // "ro ro"

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 66 / 104
Cadenas de caracteres

Conversiones
String.valueOf(v): devuelve un nuevo objeto String con la representación
del valor especificado en v (de tipo boolean, char, int, double).
Integer.parseInt(s): devuelve el resultado de obtener el valor del número
entero representado en s (de tipo String).
Integer.toString(v): devuelve un nuevo objeto String con la
representación del valor especificado en v (de tipo int).
Double.parseDouble(s): devuelve el resultado de obtener el valor del
número real representado en s (de tipo String).
Double.toString(v): devuelve un nuevo objeto String con la
representación del valor especificado en v (de tipo double).

String c1 = String.valueOf(34); // "34"


String c2 = Integer.toString(34); // "34"
String c3 = String.valueOf(3.14); // "3.14"
String c4 = Double.toString(3.14); // "3.14"
int i1 = Integer.parseInt("34"); // 34
double d1 = Double.parseDouble("3.14"); // 3.14

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 67 / 104
Arrays
Los Arrays representan objetos que contienen una colección (de longitud fija)
de elementos (componentes) de un mismo tipo o clase.
Declaración de variables de tipo array con elementos de tipo entero y de tipo Punto:
int[] lista1; Punto[] lista2;

Los arrays se pueden crear especificando cuantos elementos tienen (valor por defecto):
int[] lista3 = new int[4]; Punto[] lista4 = new Punto[t];

Se pueden crear especificando el valor inicial de los componentes (sin tamaño):


int[] lista5 = new int[] { 0, 1, 2, 3 };
Punto[] lista6 = new Punto[] { new Punto(1,2), null, new Punto(3,4) };

En la declaración de la variable de tipo array, se pueden crear especificando el valor


inicial de los componentes (sin new):
int[] lista5 = { 0, 1, 2, 3 };
Punto[] lista6 = { new Punto(1,2), null, new Punto(3,4) };

• ▸ 0 0 0 0 • ▸ / / / • ▸ 0 1 2 3 • ▸ • / •

lista3 lista4 lista5 lista6


▾ ▾
Punto Punto

1 2 3 4

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 68 / 104
Arrays
La longitud se puede consultar en la variable de instancia length.
El primer elemento de un array se encuentra en la posición 0:
Si se intenta acceder a una posición no válida del array, el sistema lanza una
excepción: IndexOutOfBoundsException.
int[] listaEnteros = new int[5];
for (int i = 0; i < listaEnteros.length; ++i){
listaEnteros[i] = i;
}
Punto[] listaPuntos = new Punto[3];
for (int i = 0; i < listaPuntos.length; ++i){
listaPuntos[i] = new Punto(i, i);
}
String[] nombres = { "ANA", "EVA", "PEPE" };
for (int i = 0; i < nombres.length; ++i) {
System.out.println(nombres[i].toLowerCase());
}

Se puede utilizar la sentencia for-each para acceder a todos los elementos de


un array:
for (int e : listaEnteros) {
System.out.println(e);
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 69 / 104
Operaciones con Arrays: Copia de Elementos

Copia de los elementos de un array: System.arraycopy()


El método de clase arraycopy() de java.lang.System permite copiar los
elementos de un array:
public static void arraycopy(Object arrayOrigen, int primIndOrigen,
Object arrayDestino, int primIndDestino,
int numeroDeElmsCopia);
El array destino debe existir y tener tantos elementos como sea necesario.
Ejemplo de utilización:
public static void main(String[] args) {
char[] arrayOrigen = {
'd','e','s','c','a','f','e','i','n','a','d','o'
};
char[] arrayDestino = new char[7];
System.arraycopy(arrayOrigen, 3, arrayDestino, 0, 7);
// arrayDestino ahora contendrá: { 'c','a','f','e','i','n','a' }
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 70 / 104
Operaciones con Arrays: Duplicación de Arrays (I)

Duplicación de un array: Arrays.copyOf()


El método de clase copyOf() de java.util.Arrays permite duplicar un
array, creando una nueva instancia.
public static TipoBase[] copyOf(TipoBase[] arrayOriginal,
int nuevaLongitud);
Si la nueva longitud especificada es diferente de la del array original:
Elimina los últimos elementos si es menor.
Añade al final valores por defecto si es mayor.
Ejemplo de utilización:
import java.util.Arrays;
public static void main(String[] args) {
int[] arrayOrigen = { 12, 4, 8, 3, 5, 203, 28 };
int[] arrayDestino1 = Arrays.copyOf(arrayOrigen, 3);
// arrayDestino1 contendrá: { 12, 4, 8 }
int[] arrayDestino2 = Arrays.copyOf(arrayOrigen, 10);
// arrayDestino2 contendrá: { 12, 4, 8, 3, 5, 203, 28, 0, 0, 0 }
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 71 / 104
Operaciones con Arrays: Duplicación de Arrays (II)

Duplicación de un array: Arrays.copyOfRange()


El método de clase copyOfRange() de java.util.Arrays permite duplicar
un array, creando una nueva instancia, copiando los elementos a partir de la
posición desde y hasta la posición hasta (sin incluirla).
public static TipoBase[] copyOfRange(TipoBase[] arrayOriginal,
int desde, int hasta);
Si la posición hasta es mayor que los elementos del array original, entonces
añade al final valores por defecto.
Ejemplo de utilización:
import java.util.Arrays;
public static void main(String[] args) {
int[] arrayOrigen = { 12, 4, 8, 3, 5, 203, 28 };
int[] arrayDestino1 = Arrays.copyOfRange(arrayOrigen, 2, 5);
// arrayDestino1 contendrá: { 8, 3, 5 }
int[] arrayDestino2 = Arrays.copyOfRange(arrayOrigen, 5, 9);
// arrayDestino2 contendrá: { 203, 28, 0, 0 }
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 72 / 104
Operaciones con Arrays: toString

Representación String: Arrays.toString()


El método de clase toString() de java.util.Arrays devuelve un nuevo
objeto String con la representación del contenido de un array.
El método de clase deepToString() de java.util.Arrays devuelve un
nuevo objeto String con la representación del contenido de un array
multi-dimensional.
static String toString(TipoBase[] array); // [a1, a2, ..., an]
static String deepToString(Object[] array); // [a1, a2, ..., an]
Ejemplo de utilización:
import java.util.Arrays;
public static void main(String[] args) {
int[] array = { 1, 3, 5, 7, 9 };
System.out.println(Arrays.toString(array));
// muestra [1, 3, 5, 7, 9]
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 73 / 104
Operaciones con Arrays: Comparación y Búsqueda

Comparación y Búsqueda. Arrays.equals() y Arrays.binarySearch()


El método de clase equals() de java.util.Arrays devuelve true si los
contenidos de dos arrays son iguales.
public static boolean equals(TipoBase[] a1, TipoBase[] a2);
El método de clase binarySearch() de java.util.Arrays devuelve el
índice donde se encuentra un determinado valor en un array ordenado
(negativo si no lo encuentra).
public static int binarySearch(TipoBase[] array, TipoBase valor);
Ejemplo de utilización:
import java.util.Arrays;
public static void main(String[] args) {
int[] array1 = { 1, 3, 5, 7, 9 };
System.out.println(Arrays.binarySearch(array, 5)); // muestra 2
int[] array2 = { 1, 3, 5, 7, 9 };
if (Arrays.equals(array1, array2)) {
System.out.println("Iguales");
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 74 / 104
Arrays Multidimensionales
Los elementos de un array también pueden ser arrays, dando lugar a a los
arrays multi-dimensionales.
int[][] a = new int[2][3];
int[][] b = new int[][] { { 3, 4, 5 }, { 6, 7, 8 } };
int[][] c = { { 3, 4, 5 }, { 6, 7, 8 } };
double[][][] d = new double[3][5][4];

a b
▸ 0 0 0 ▸ 3 4 5
• ▸ • • ▸ •

• ▸ 0 0 0 • ▸ 6 7 8

El uso más común de arrays multidimensionales es el array de dos dimensiones.


También es posible crear un array multidimensional creando cada componente
(dimensión) paso a paso, e incluso con tamaños diferentes.
int[][] x = new int[2][];
for (int i = 0; i < x.length; i++) {
x[i] = new int[i + 2];
for (int j = 0; j < x[i].length; j++) {
x[i][j] = i + j;
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 75 / 104
Ejemplo: la clase Concesionario

Defina una clase Concesionario que modele el concepto de una colección de


coches (Coche).
Como estado interno de los objetos, almacenará tanto el numero de coches
almacenados, como el array que almacena la secuencia de coches del objeto.
Proporcionará los siguientes constructores y métodos públicos:
Ctor. por defecto, crea una colección vacía (sin elementos), con una capacidad
inicial de TAM (10).
Ctor(t), crea una colección vacía (sin elementos), con la capacidad inicial recibida
como parámetro.
Añadir un coche, considerando que si ya existe en la colección otro coche con el
mismo modelo, el coche existente será reemplazado por el nuevo coche.
Eliminar un coche de la colección a partir del modelo, considerando que si no
existe se lanzará una excepción.
Acceder al coche más barato de la colección. Si la colección está vacía, lanzará
una excepción.
Representación textual del objeto (toString()).

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 76 / 104
Clases anidadas: clases anidadas estáticas

Las clases anidadas se definen dentro de la definición de otra clase.


Aunque se pueden distinguir diversos tipos de clases anidadas (estáticas,
internas, locales, anónimas), solo consideraremos las denominadas clases
anidadas estáticas.
Una clase anidada estática se define como un miembro más de la clase,
especificando su nivel de visibilidad y el calificador static.
Para acceder a ellas desde el exterior, si es pública, se debe cualificar su nombre
con el nombre de la clase externa a la que pertenece (Segmento.Punto).
public class Segmento {
public static class Punto {
private double x, y;
// ...
}
private Punto origen, extremo;
// ...
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 77 / 104
Tipos de Datos enumerados: enum (I)
Los tipos de datos enumerados se caracterizan por definir una serie de valores que
forman parte de la enumeración.
Se definen especificando el nombre del tipo y los valores de la enumeración.
// fichero Color.java
public enum Color {
Negro, Rojo, Verde, Azul, Amarillo, Magenta, Cian, Blanco
}
Se pueden declarar variables y parámetros de tipos enumerados, y usar sus valores
donde sea necesario.
Cada valor de la enumeración se puede utilizar cualificándolo con el nombre del
tipo enumerado: Color.Rojo.
Java proporciona automáticamente los siguientes métodos asociados a la clase
enumerada: values(), valueOf(str), ordinal(), toString(), equals(v),
hashCode(), compareTo(v).
public class Main {
public static void main(String[] args) {
Color s = Color.Negro; // primer valor de la enumeración
Color t = Color.valueOf("Rojo"); // valor asociado al String
int ord = s.ordinal(); // ordinal asociado al valor (0 ...)
for(Color se : Color.values()) { // Color[] con todos los valores
System.out.print(" " + se.toString());
}
// muestra: Negro Rojo Verde Azul Amarillo Magenta Cian Blanco
}
Dpto. } y Ciencias de la Computación. E.T.S.I. Informática.
Lenguajes Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 78 / 104
Tipos de Datos enumerados: enum (II)

También es posible definir tipos de datos enumerados como clases


anidadas estáticas.
public class Ejemplo {

public static enum Color {


Negro, Rojo, Verde, Azul, Amarillo, Magenta, Cian, Blanco
}

public static void main(String[] args) {


Color s = Color.Negro; // primer valor de la enumeración
Color t = Color.valueOf("Rojo"); // valor asociado al String
int ord = s.ordinal(); // ordinal asociado al valor (0 ...)
for(Color se : Color.values()) { // Color[] con todos los valores
System.out.print(" " + se.toString());
}
// muestra: Negro Rojo Verde Azul Amarillo Magenta Cian Blanco
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 79 / 104
Herencia
La Herencia representa una relación en la cual una clase (subclase) es una
especialización o extensión de otra clase (superclase) más general.
Se puede definir una clase (subclase) que hereda de otra clase (superclase)
de la siguiente forma:
public class SubClase extends SuperClase { /* ... */ }

La subclase hereda tanto los atributos como los métodos definidos por la
superclase (reusabilidad del código).
La subclase puede definir nuevos atributos y nuevos métodos (extensión), así
como redefinir métodos de la superclase (especialización).

SuperClase Punto Coche Persona

^ ^ ^ ^

SubClase Particula CocheColor Paciente Médico

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 80 / 104
Herencia
Java sólo permite herencia simple, por lo que pueden establecerse jerarquías
de clases (una clase sólo puede heredar de una única clase, pero puede tener
varias clases herederas).
La relación de herencia es transitiva, si C hereda de B y B hereda de A,
entonces C también hereda de A.
Todas las clases son herederas directas o indirectas de la clase Object de
java.lang que define los comportamientos básicos que debe presentar
cualquier clase (entre otros, toString(), equals(o) y hashCode()).

Object
^

Punto Persona Coche


^ ^ ^

Particula ... Paciente Médico Alumno CocheColor

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 81 / 104
Ejemplo: Clase CocheColor

La clase CocheColor representa información sobre las características de un


coche, que además tiene información sobre el color del mismo.
Los posibles colores que puede tener un coche de color, y el incremento del
color en el precio base del coche son:
Negro: 0, Rojo: 10, Verde: 20, Azul: 30, Amarillo: 40, Magenta: 50, Cian: 60, Blanco: 70.

Proporcionará los siguientes constructores y métodos públicos:

Ctor. además del modelo y su precio base, se debe especificar el color del coche,
tanto en String como con el valor del tipo enumerado Color.
Consultar y modificar el color del coche.
Ahora, el nombre del modelo lleva añadido el color del coche.
El valor del precio base será incrementado con el precio del color del coche.
Consultar los colores disponibles.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 82 / 104
Ejemplo: Clase CocheColor
public class CocheColor extends Coche {
// Negro: 0, Rojo: 10, Verde: 20, Azul: 30, Amarillo: 40, Magenta: 50, Cian: 60, Blanco: 70
private static final double PRECIO_COLOR = 10.0; // Atributos ( + los heredados de Coche
private Color color;
public CocheColor(String m, double p, String c) {
this(m, p, Color.valueOf(c)); // invocación a CocheColor(String, double, Color)
}
public CocheColor(String m, double p, Color c) {
super(m, p); // invocación a Coche(String, double)
color = c;
}
public Color getColor() { return color; } // Métodos ( + los heredados de Coche )
public void setColor(Color c) { color = c; }
public void setColor(String c) { color = Color.valueOf(c); }
@Override // redefinición del método getModelo() de Coche
public String getModelo() {
return super.getModelo() + " " + this.getColor().toString();
}
@Override // redefinición del método getPrecioBase() de Coche
protected double getPrecioBase() {
return super.getPrecioBase() + this.getColor().ordinal() * PRECIO_COLOR;
}
public static String[] coloresDisponibles() {
Color[] cs = Color.values();
String[] res = new String[cs.length];
for (int i = 0; i < res.length; ++i) {
res[i] = cs[i].toString();
}
return res;
} y Ciencias de la Computación. E.T.S.I. Informática.
Dpto. Lenguajes Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 83 / 104
Herencia y constructores
Los constructores no se heredan.
Cuando se define un constructor de una subclase se debe proceder de alguna de las
tres formas siguientes:
Invocar a un constructor de la misma clase (con distintos argumentos) mediante
this (debe ser la primera línea):
public CocheColor(String m, double p, String c) {
this(m, p, Color.valueOf(c)); // invocación a CocheColor(String, double, Color)
}

Invocar a algún constructor de la superclase mediante super (debe ser la


primera línea):
public CocheColor(String m, double p, Color c) {
super(m, p); // invocación a Coche(String, double)
color = c;
}

En otro caso, se invoca automáticamente por defecto al constructor sin


argumentos de la superclase (puede ser un error si no existe el constructor):
public CocheColor(String m, double p, Color c) {
// invocación automática a Coche() // ERROR el constructor Coche() no existe
color = c;
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 84 / 104
Herencia y Polimorfismo
El polimorfismo permite que un objeto de una subclase pueda ser considerado y
referenciado como un objeto de la superclase. Principio de sustitución. Ej. todo
coche con color es un coche.
Una variable del tipo de la superclase puede referenciar a un objeto de la subclase.
Coche coche = new CocheColor("Ferrari", 50000, Color.Rojo);

El tipo estático es el tipo de la variable (tiempo de compilación). El tipo dinámico


es el tipo del objeto al que referencia la variable (tiempo de ejecución).
En contextos polimórficos, sólo es válido invocar a los métodos especificados por el
tipo estático de la variable.
Coche coche = new CocheColor("Ferrari", 50000, Color.Rojo);
double precio = coche.calcPrecioFinal(); // Correcto
// coche.setColor(Color.Verde); // ERROR. No es posible

Se puede forzar la conversión de tipos de la superclase a la subclase, pero hay que


estar seguros (instanceof), ya que no todos los objetos de la superclase son también
objetos de la subclase. El abuso de instanceof es síntoma de un mal diseño.
Coche coche = new CocheColor("Ferrari", 50000, Color.Rojo);
double precio = coche.calcPrecioFinal(); // Correcto
if (coche instanceof CocheColor) {
CocheColor cocheColor = (CocheColor)coche; // Correcto
cocheColor.setColor(Color.Verde); // Correcto
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 85 / 104
Herencia y redefinición del comportamiento

Una subclase puede redefinir algún método heredado (no deben ser ni
private ni final ni static).
En la subclase, el método redefinido de la superclase queda oculto por el nuevo
método. Se puede invocar al método oculto de la superclase:
super.nombreDelMétodo(argumentos)
La anotación @Override ayuda a detectar errores al redefinir el método, tales
como errores en el nombre o en la lista de parámetros del método que está
siendo redefinido.
public class CocheColor extends Coche {
// ...
@Override // redefinición del método getModelo() de Coche
public String getModelo() {
return super.getModelo() + " " + this.getColor().toString();
}
@Override // redefinición del método getPrecioBase() de Coche
protected double getPrecioBase() {
// Precio del Color: Negro: 0, Rojo: 10, Verde: 20, Azul: 30,
// Amarillo: 40, Magenta: 50, Cian: 60, Blanco: 70
return super.getPrecioBase() + this.getColor().ordinal() * PRECIO_COLOR;
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 86 / 104
Herencia y Vinculación Dinámica

La vinculación dinámica resulta el complemento indispensable del polimorfismo.


En contextos polimórficos, sólo es válido invocar a los métodos especificados
por el tipo estático de la variable.
En contextos polimórficos, la ejecución del método invocado se selecciona
adecuadamente, en tiempo de ejecución, dependiendo del tipo dinámico del
objeto, y no del tipo estático de la variable que lo referencia.
La invocación del método que ha de resolver un mensaje se retrasa al tiempo de
ejecución, y depende del tipo dinámico del objeto.
Coche coche1 = new Coche("Porsche", 40000);
Coche coche2 = new CocheColor("Ferrari", 50000, Color.Rojo);
// ---
String modelo1 = coche1.getModelo(); // "Porsche"
String modelo2 = coche2.getModelo(); // "Ferrari Rojo"
double precioFinal1 = coche1.calcPrecioFinal(); // 44110 (40000+100)*(1+0.1)
double precioFinal2 = coche2.calcPrecioFinal(); // 55121 (50000+10+100)*(1+0.1)
String txt1 = coche1.toString(); // "(1, Porsche, 44110)"
String txt2 = coche2.toString(); // "(2, Ferrari Rojo, 55121)"

La resolución de la invocación a los métodos de instancia se realiza por vinculación


dinámica (en tiempo de ejecución).

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 87 / 104
Prohibiendo subclases

Por razones de seguridad o de diseño, se puede prohibir la definición de


subclases para una clase etiquetándola con final.
Recordad que una subclase puede sustituir a su superclase donde ésta sea
necesaria y tener comportamientos muy distintos.

El compilador rechazará cualquier intento de definir una subclase para una


clase etiquetada con final.
También se pueden etiquetar con final:
Métodos, para evitar su redefinición en alguna posible subclase.
Variables, para mantener constantes sus valores o referencias.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 88 / 104
Promoviendo subclases: Clases abstractas (I)
A veces, una clase puede definir una abstracción de datos incompleta, porque no
le sea posible proporcionar una definición completa de todos los métodos de la clase,
pero sin embargo, sí puede proporcionar una especificación abstracta del
comportamiento esperado de los objetos de la clase.
Estas clases se califican como abstract y pueden tener métodos sin definición
(sin cuerpo), que también son calificados como abstract.
public abstract class CocheAbstracto {
// variables de instancia y de clase ...
public CocheAbstracto(String m) { /* ... */ }
public int getRef() { /* ... */ }
public String getModelo() { /* ... */ }
public abstract double calcPrecioFinal() ; // método abstracto (sin cuerpo)
}
No es posible crear objetos (instancias) de clases abstractas. Se deben definir
subclases que no sean abstractas para poder crear objetos.
Las subclases deben definir adecuadamente los métodos abstractos de la
superclase, según la abstración que modelen.
Si una subclase no define algún método abstracto de la superclase, entonces
esta subclase también será abstracta.
Las clases abstractas se utilizan para formar jerarquías de clases, proporcionando
definiciones de comportamientos abstractos y comunes.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 89 / 104
Promoviendo subclases: Clases abstractas (II)
Por ejemplo, la clase CocheAbstracto modela una abstracción de coche, sin
embargo, no puede proporcionar una implementación adecuada para el cálculo
del precio del coche, ya que depende del tipo de coche concreto. Esta
operación deberá ser proporcionada por las subclases.
public abstract class CocheAbstracto {
private static int refCnt = 1;
private final int referencia;
private final String modelo;
public CocheAbstracto(String m) {
modelo = m;
referencia = refCnt;
++refCnt;
}
public int getRef() {
return referencia;
}
public String getModelo() {
return modelo;
}
public abstract double calcPrecioFinal() ; // método abstracto (sin cuerpo)
@Override
public String toString() {
return "(" + getRef() + ", " + getModelo() + ", " + calcPrecioFinal() + ")";
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 90 / 104
Promoviendo subclases: Clases abstractas (III)

public class CocheNacional extends CocheAbstracto {


private static final double IVA = 10.0;
private double precio;
public CocheNacional(String m, double p) {
super(m);
precio = p;
}
@Override
public double calcPrecioFinal() { // redefine el método abstracto
return precio + precio * IVA / 100.0;
}
}

public class CocheImportado extends CocheAbstracto {


private static final double IMPUESTO_IMPORTACION = 1000.0;
private double precio;
public CocheImportado(String m, double p) {
super(m);
precio = p;
}
@Override
public double calcPrecioFinal() { // redefine el método abstracto
return precio + IMPUESTO_IMPORTACION;
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 91 / 104
Interfaces (I)
Una interfaz especifica un comportamiento, metodos abstractos, que deben ser
implementados por cualquier clase que pretenda ofrecer ese comportamiento (por
cualquier clase que implemente esa interfaz).
El objetivo principal de una interfaz es especificar los métodos abstractos que
deben ser implementados por las clases que implementen esta interfaz.
Además, una interfaz también puede definir métodos por defecto, métodos de
clase, constantes de clase y clases e interfaces anidadas.
public interface Conjunto {
int ERROR = -1 ; // public static final

void anyadir(int val) ; // public abstract


void eliminar(int val) ; // public abstract
boolean pertenece(int val) ; // public abstract
int consultar(int pos) ; // public abstract
int size() ; // public abstract

default boolean estaVacio() { // public default


return size() == 0;
}

static boolean esError(int c) { // public static


return c == ERROR;
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 92 / 104
Interfaces (II)

Una interfaz puede extender (heredar) a múltiples interfaces, heredando el


comportamiento definido por ellas, así como añadir nuevos métodos.
Una interfaz sólo puede ser extendida por otra interfaz.
Una interfaz incorpora implícitamente los métodos públicos de Object.

public interface Estadisticas {


double media() ; // public abstract
}

public interface ConjuntoEstadisticas extends Conjunto , Estadisticas {


// métodos y constantes heredados (+)
int[] exportar(); // public abstract
}

No es posible crear objetos (instancias) de las interfaces. Se deben definir clases


que implementen la interfaz para poder crear objetos.

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 93 / 104
Implementación de Interfaces

Una clase puede implementar a varias interfaces, además de heredar de una única
clase. Deberá implementar los métodos abstractos especificados por la interfaz.
Cuando una clase implementa una interfaz:
Hereda todas las constantes definidas en la interfaz y en sus superinterfaces.
Debe implementar todos los métodos definidos por la interfaz y sus
superinterfaces. Salvo que sea una clase sea abstracta, en cuyo caso los
métodos no implementados son abstract.
Un objeto, de una clase que implementa una interfaz, puede ser utilizado
(polimórficamente) en cualquier sitio donde sea necesario un objeto que
implemente la interfaz especificada.
public class Datos extends SuperClase implements Conjunto, Estadisticas, ... {
// Debe implementar los métodos especificados en la interfaz Conjunto
public void anyadir(int val) { /* ... */ }
public void eliminar(int val) { /* ... */ }
public boolean pertenece(int val) { /* ... */ }
public int consultar(int pos) { /* ... */ }
public int size() { /* ... */ }
// Debe implementar los métodos especificados en la interfaz Estadisticas
public double media() { /* ... */ }
// Otras variables y métodos adicionales de la clase ...
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 94 / 104
Diagrama UML de Clases e Interfaces
La composición de clases se expresa en UML mediante una línea sólida con punta
de flecha con la punta abierta entre la clase poseedora y la clase poseída.
La herencia de clases se expresa en UML mediante una línea sólida desde la
subclase con un triángulo hueco en el extremo de la superclase.
La herencia de interfaces se expresa en UML mediante una línea sólida desde la
sub-interfaz con un triángulo hueco en el extremo de la super-interfaz.
La implementación de interfaces se expresa en UML mediante una línea
discontinua desde la clase con un triángulo hueco en el extremo de la interfaz.

C SuperClase «interface» «interface»


I Interfaz I Interfaz

extends implements extends

C SubClase obj C Clase obj «interface»


I Interfaz
0.. 0..
* *
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 95 / 104
Ejemplo de Implementación de Interfaces (I)
public class Datos implements Conjunto, Estadisticas {
private int[] datos;
private int ndatos;
public Datos() {
datos = new int[32];
ndatos = 0;
}
@Override
public int size() {
return ndatos;
}
@Override
public void anyadir(int val) {
if ( ! pertenece(val) ) {
if (ndatos == datos.length) {
datos = java.util.Arrays.copyOf(datos, 2*datos.length);
}
datos[ndatos] = val;
++ndatos;
}
}
@Override
public void eliminar(int val) {
int pos = buscar(val);
if (pos >= 0) {
datos[pos] = datos[ndatos-1];
--ndatos;
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 96 / 104
Ejemplo de Implementación de Interfaces (II)
@Override
public boolean pertenece(int val) {
return buscar(val) >= 0;
}
@Override
public int consultar(int pos) {
if (pos < 0 || pos >= ndatos) {
throw new IllegalArgumentException("posición erronea");
}
return datos[pos];
}
@Override
public double media() {
if ( estaVacio() ) {
throw new RuntimeException("sin datos");
}
int suma = 0;
for (int i = 0; i < ndatos; ++i) {
suma += datos[i];
}
return (double) suma / (double) ndatos;
}
private int buscar(int val) {
int i = 0;
while ((i < ndatos) && (val != datos[i])) {
++i;
}
return i < ndatos ? i : -1;
}
} Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Dpto. Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 97 / 104
Uso de interfaces
No es posible crear instancias (objetos) de una interfaz.
Podemos declarar variables y parámetros del tipo definido por una interfaz, que
pueden hacer referencia a cualquier objeto de una clase (y de las herederas de ella)
que implementa la interfaz (Polimorfismo).
public class MainDatos {
private static void anyadirElementosAConjunto(Conjunto conjunto) {
conjunto.anyadir(3);
conjunto.anyadir(4);
conjunto.anyadir(5);
conjunto.eliminar(4);
}
private static void mostrarConjunto(Conjunto conjunto) {
for (int i = 0; i < conjunto.size(); ++i) {
System.out.print(conjunto.consultar(i) + " ");
}
System.out.println();
}
private static void mostrarEstadisticas(Estadisticas sts) {
System.out.println(sts.media());
}
public static void main(String[] args) {
Datos datos = new Datos();
anyadirElementosAConjunto(datos);
mostrarEstadisticas(datos);
mostrarConjunto(datos);
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 98 / 104
Interfaces como Abstracción Funcional
La abstracción funcional especifica un comportamiento abstracto (tarea, operación,
cálculo, funcionalidad, etc), sin determinar como será realizado.
Las interfaces proporcionan soluciones elegantes a problemas donde se desea aplicar
a los datos un procesamiento flexible y adaptable a diferentes contextos
(denominamos abstracción funcional a este procesamiento abstracto).
Allí donde sea necesaria la funcionalidad especificada por la interfaz, se podrá utilizar
una clase que implemente dicha interfaz. Diferentes clases podrán proporcionar
diferentes implementaciones de dicha funcionalidad, haciendo de este mecanismo
algo flexible y adaptable a diferentes contextos.
Por ejemplo, supongamos la clase Concesionario que contiene una colección de
coches.
Podemos añadir, acceder y mostrar los coches.
También podemos seleccionar a los coches según diferentes criterios.
Por cada criterio, habrá que implementar un nuevo método.
Si deseamos añadir un nuevo criterio en el futuro, deberemos modificar la clase
para añadir un nuevo método.
Es más adecuado, flexible y adaptable definir el criterio de selección como una
interfaz que proporcione una abstracción funcional sobre dicho criterio de
selección.
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 99 / 104
Ejemplo sin Interfaces (I)
La clase Concesionario permite almacenar una colección de coches, así
como seleccionarlos según diferentes criterios (precio, color, etc.):
import java.util.Arrays;
public class Concesionario {
private Coche[] coches;
private int numCoches;
public Concesionario() {
coches = new Coche[16];
numCoches = 0;
}
public Coche[] seleccionarPrecio(double a, double b) {
Coche[] r = new Coche[numCoches];
int x = 0;
for (int i = 0; i < numCoches; ++i) {
double p = coches[i].calcPrecioFinal();
if (a <= p && p < b) {
r[x] = coches[i];
++x;
}
}
return Arrays.copyOf(r, x);
}
public void anyadir(Coche c) { /* ... */ }
public String toString() { /* ... */ }
// ... Otros métodos ...
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 100 / 104
Ejemplo sin Interfaces (II)

Podemos utilizar la clase Concesionario para almacenar y seleccionar los


coches según diferentes criterios (precio, color, etc.):
import java.util.Arrays;
public class Main {
public static void main(String[] args) {
Concesionario c = new Concesionario();
c.anyadir(new Coche("Porsche", 40000));
c.anyadir(new CocheColor("Ferrari", 50000, Color.Rojo));
c.anyadir(new CocheColor("Audi", 30000, Color.Rojo));
c.anyadir(new Coche("Mercedez", 35000));
c.anyadir(new CocheColor("Toyota", 20000, Color.Azul));
System.out.println(c);
Coche[] sel = c.seleccionarPrecio(30000, 40000);
System.out.println(Arrays.toString(sel));
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 101 / 104
Ejemplo con Interfaces como Abstracción Funcional (I)
La utilización de interfaces proporciona una solución más flexible y adaptable.
La interfaz SelectorCoche especifica el criterio de selección:
public interface SelectorCoche {
public boolean esSeleccionable(Coche p);
}

La clase SelectorPrecio implementa la selección por precio:


public class SelectorPrecio implements SelectorCoche {
private double min, max;
public SelectorPrecio(double min, double max) {
this.min = min; this.max = max;
}
public boolean esSeleccionable(Coche c) {
double p = c.calcPrecioFinal();
return (min <= p && p < max);
}
}
La clase SelectorColor implementa la selección por color:
public class SelectorColor implements SelectorCoche {
private String color;
public SelectorColor(String c) {
this.color = c.toLowerCase();
}
public boolean esSeleccionable(Coche c) {
return c.getModelo().toLowerCase().contains(color);
}
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 102 / 104
Ejemplo con Interfaces como Abstracción Funcional (II)
La clase Concesionario utiliza la clase que implemente la interfaz
SelectorCoche como criterio de selección, a través del método
esSeleccionable():
import java.util.Arrays;
public class Concesionario {
private Coche[] coches;
private int numCoches;
public Concesionario() {
coches = new Coche[16];
numCoches = 0;
}
public Coche[] seleccionar(SelectorCoche p) { // el selector especifica el criterio
Coche[] r = new Coche[numCoches];
int x = 0;
for (int i = 0; i < numCoches; ++i) {
if (p.esSeleccionable(coches[i])) { // invoca al método sobre el objeto selecto
r[x] = coches[i];
++x;
}
}
return Arrays.copyOf(r, x);
}
public void anyadir(Coche c) { /* ... */ }
public String toString() { /* ... */ }
// ... Otros métodos ...
}
Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.
Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 103 / 104
Ejemplo con Interfaces como Abstracción Funcional (III)

La clase que invoca al método de selección especifica el criterio para


seleccionar según la clase del objeto que proporcione como argumento:
import java.util.Arrays;
public class Main {
public static void main(String[] args) {
Concesionario c = new Concesionario();
c.anyadir(new Coche("Porsche", 40000));
c.anyadir(new CocheColor("Ferrari", 50000, Color.Rojo));
c.anyadir(new CocheColor("Audi", 30000, Color.Rojo));
c.anyadir(new Coche("Mercedez", 35000));
c.anyadir(new CocheColor("Toyota", 20000, Color.Azul));
System.out.println(c);
Coche[] sel1 = c.seleccionar(new SelectorPrecio(30000, 40000));
System.out.println(Arrays.toString(sel1));
Coche[] sel2 = c.seleccionar(new SelectorColor("Rojo"));
System.out.println(Arrays.toString(sel2));
}
}

Dpto. Lenguajes y Ciencias de la Computación. E.T.S.I. Informática.


Tema
Universidad
2. Introducción
de Málaga
a Java Programación Orientada a Objetos 104 / 104

También podría gustarte