2025-01-13-Programacion - Contenido educativo
Ajuste de pantallaEl ajuste de pantalla se aprecia al ver el vídeo en pantalla completa. Elige la presentación que más te guste:
Tema 5. Alcance variables, getters y setters, etiqueta final, constructor copia
Ya estamos en marcha, pues como decíamos antes, feliz año a todos y bueno, pues vamos a arrancar. En un poco más de un mes o en un mes más o menos tenemos el examen este de prueba.
00:00:01
comentaros el examen acordaros que bueno pues en realidad ni quita contenidos para el examen final
00:00:13
cosa que al final sería un poquito lo que estamos viendo hasta ahora es necesario en todo programa
00:00:23
de java con lo cual el quitar contenidos o no quitar contenido no llevaría a ningún sitio pero
00:00:30
bueno no es el caso no quita no quita ningún tipo de materia pero sí que creo que es bastante
00:00:34
interesante, si podéis sacar
00:00:39
el ratito con vuestros trabajos, que sé que
00:00:41
todos estáis, bueno, pues lleváis
00:00:43
vidas atareadas, ¿no? Y con vuestros
00:00:45
trabajos y en muchos casos
00:00:47
con cargas familiares y todo.
00:00:49
Pero si tenéis el ratito
00:00:52
para venir a hacer el examen, creo que es interesante
00:00:53
porque el esquema
00:00:55
del examen es, claro,
00:00:57
cuando hagamos en
00:01:00
para la ordinaria el examen, luego hacía
00:01:01
cerca de junio, finales de mayo
00:01:03
o principios de junio, ya estaban las fechas por ahí
00:01:05
puestas, no las recuerdo.
00:01:07
Habrá más contenidos, pero el modelo del examen es prácticamente igual en cuanto a la estructura y en cuanto al tipo de preguntas, digamos, para que os podáis hacer una idea. Entonces creo que resulta útil el que vengáis a hacerlo.
00:01:09
Si tenéis el ratillo, interesante que os paséis. Y nada, pues el examen abre un tema ahora el día 21 en una semana, abre un tema nuevo, pues hasta el siguiente tema. Nos entrarán los contenidos de los cuales sacaremos las preguntas para el examen.
00:01:24
¿Cómo suele ser? Pues suele tener, lo anticipo un poco, pues algunas preguntas tipo test, algunas que tengáis que responder verdadero o falso, alguna que tenga opciones para resolverlo y luego pues os pedirá un enunciado en el cual tendréis que hacer algunos pequeños programas, no muy grandes, pero bueno, o de algún programa, a lo mejor os lo pedimos por apartados.
00:01:46
aquí haz un constructor copia, aquí haz
00:02:10
un método que se llame
00:02:14
no sé qué, que reciba tal y de como resultado
00:02:16
pues otra cosa. Entonces bueno, pues hay que
00:02:19
darle un poquillo a la cabeza para ver cómo podría ser el algoritmo que
00:02:22
resuelva ese problema que se plantea
00:02:25
y bueno, pues implementarlo con las cosas
00:02:28
que estamos viendo, en principio
00:02:31
lógicamente basado en el lenguaje Java
00:02:34
que es el que estamos utilizando en la asignatura.
00:02:37
Y dicho esto, pues nada, preguntaros si tenéis alguna duda o alguna consulta que me queráis hacer
00:02:44
antes de arrancar yo a contaros algunas cosas. Por ahí están dos horitas que tenemos por delante.
00:02:48
Se me escucha bien, eso sí, ¿verdad? Vale.
00:02:57
¿Alguna cosita por ahí queréis que comentemos o arranco por aquí?
00:03:08
Y tengo el último día de clase, que tuvimos solamente una hora, estuvimos resolviendo la tarea del tema 4.
00:03:12
Recuerdo que quedó un poco... bueno, pues no nos dio tiempo a probarlo.
00:03:21
Al final habíamos metido todo el código, hicimos una prueba y tenía algún fallo, me parece, que no nos dio tiempo a depurar.
00:03:26
Yo creo que en principio, si no me lo pedís de forma explícita, pues lo dejamos ya parado aquello,
00:03:33
porque digamos que la vuelta teórica ya la había mordado y arrancamos con cosas relacionadas con lo que tenéis en la teoría del tema 5.
00:03:38
¿Os parece? Vale, pues ahora, pues venga, pues vamos ahí al ataque.
00:03:47
El tema 5 todavía continúa siendo, bueno y el tema 6 incluso, continúa haciéndonos aterrizar en la programación orientada a objetos
00:03:55
y claro, como desde el primer día para hacer programas
00:04:05
hemos venido utilizando programas en Java, que es un lenguaje como ya hemos comentado
00:04:10
orientado a objetos, pues poco a poco, sin querer o a propósito
00:04:14
hemos ido adelantando muchos de los conceptos, entonces aquí digamos que
00:04:18
formalmente en este tema 5, pues asentamos algunos de ellos
00:04:22
Bueno, como repaso para los que no hayamos
00:04:25
para aquellos que no hayamos visto y para los que sí que hemos visto
00:04:29
pues ir asentándolos, pues vamos a dedicar un par de tutorías, la de esta y la de la semana que viene
00:04:33
y luego ya la semana que viene, el martes, arranca ya el siguiente tema, ya lo concluimos entre estas dos semanas
00:04:39
y repasamos cositas. Y para repasar los conceptos, pues como siempre, me parece que lo más útil es ir haciéndolo
00:04:47
con Eclipse, pues vamos con ello. Vamos a arrancar un proyecto, aquí, que podemos llamar por ejemplo
00:04:53
lo tema 5. En este tema, bueno, pues habla, creo recordar, lo estuve leyendo justo a principio de
00:05:02
navidades repasando los contenidos de este tema, pues bueno, hablaba de las clases y los objetos,
00:05:16
un poco lo que los diferenciaba, las clases, yo lo cuento más o menos bien al ser lo mismo, pero bueno,
00:05:22
lo cuento un poco con mis palabras o como yo lo veo, que quizás no coincida al 100% con lo que
00:05:28
ponga ahí en los apuntes, aunque claro no es muy lejanos, las clases vienen a ser el esquema en el
00:05:33
cual definimos las características o atributos que tienen los objetos de esa clase que luego
00:05:41
vamos a ir instanciando y los métodos como formas de comportamiento. Ese esquema yo siempre digo lo
00:05:48
colgamos ahí como un cuadro por ejemplo en la pizarra, lo dibujamos en la pizarra, lo colgamos
00:05:55
en la pared y normalmente una clase no es la que está interactuando y la que está poniendo en
00:05:59
marcha el programa, sino que son objetos de esa clase que vamos creando
00:06:04
según vayamos necesitándolos. No doy muchas más vueltas al
00:06:08
concepto de clase y objetos porque ya hemos hablado de ellos.
00:06:12
Y luego también creo recordar que en el tema se habla
00:06:16
algo de métodos y parámetros. Los métodos son aquellas acciones
00:06:20
que hacen los objetos de una clase y que vienen definidos
00:06:24
en la clase como esquema base del comportamiento
00:06:28
de esa clase y de los objetos que luego vayamos instanciando
00:06:32
de ellos. Y los parámetros, pues esa información
00:06:35
que dentro del método se va a comportar como variables
00:06:38
locales que ponemos entre los paréntesis
00:06:41
en la definición con el tipo
00:06:44
y cuando hacemos llamadas ponemos los valores que se copian
00:06:47
directamente para la ejecución del método.
00:06:50
Lo tenemos súper trabajado esto.
00:06:53
Y luego, no sé si es exactamente en este
00:06:56
orden en el que lo va contando en el tema, pero
00:07:00
sí en el guión del tema que me he hecho yo, tengo apuntado a hablaros de un poquito del ámbito de
00:07:02
alcance de las clases. Bueno, hay diferentes tipos de etiquetas y una de las cosas que nos aparecen
00:07:10
es el ámbito de alcance dentro de un proyecto, es decir, que sean públicos, que sean protective, que
00:07:18
sean friendly o package, que viene a ser aquellos en los cuales no definimos el tipo de alcance o
00:07:24
que sean privados. Vamos aquí en el tema 5 a crear un paquete. Normalmente sabéis que no suelo
00:07:31
trabajar utilizando paquetes porque como son programas muy pequeños pues directamente
00:07:39
utilizo el paquete por defecto pero en este caso sí que lo vamos a hacer acá. Vamos a definirlos
00:07:44
porque tiene que ver con el alcance de desde dónde podemos llegar a métodos de otras clases
00:07:50
diferentes. Vamos a definir un primer paquete, paquete 1, package 1 lo he llamado, y vamos a definir un segundo
00:07:57
paquete por aquí, package 2. Recordad que al final podríamos tener todo el código en un solo paquete,
00:08:05
que la forma de que esté distribuido en el sistema de archivos sería en un solo directorio del proyecto,
00:08:17
mirad aquí en el directorio home del usuario Debian en Eclipse
00:08:25
tenemos el directorio Eclipse Workspace
00:08:33
que está asociado a Eclipse para ir guardando los diferentes proyectos
00:08:36
y aquí si hacemos un ls vemos todos los proyectos que tenemos dados de alta dentro de Eclipse
00:08:40
en este caso estamos en el proyecto tema 5
00:08:47
tenemos un directorio colgando el Workspace completo
00:08:51
Y aquí tenemos el código fuente, aquí y por aquí en el bin tendríamos los ficheros .class. Dentro de los ficheros .class fijaros como nos han aparecido de repente dos directorios aquí que corresponde cada uno a cada uno de los dos paquetes que tenemos.
00:08:54
¿Para qué nos resultan útiles los paquetes? Volviendo a ejemplos que hemos utilizado en otras ocasiones, imaginaos que tenemos un proyecto que estamos haciendo de un banco y podríamos tener todo el código en un directorio, en un único paquete, todo el código ahí puesto.
00:09:17
En el momento en el que el proyecto ya es un proyecto con cierta envergadura, nos saldrían un montón de ficheros. Todos estos ficheros estarían dando funcionalidades al banco probablemente en diferentes ámbitos.
00:09:34
Pues unos pertenecerían a la parte de líneas de crédito, otros pertenecerían al pago de nóminas, bueno, vete tú a saber, ¿no? Otro al banco, pero en su sección de recursos humanos. Pues si tenemos código para todos estos campos y muchos otros, todos ellos en un único paquete, pues seguramente su mantenimiento nos resulte más costoso.
00:09:48
entonces que podemos hacer para proyectos así grandes pues crear diferentes paquetes y uno de
00:10:10
los paquetes que aquí lo llamado yo para cada uno y para cada dos pues podría ser recursos humanos
00:10:16
y otro nóminas y de esta forma el código de cada uno de ellos meterlo dentro de su paquete con lo
00:10:20
cual queda todo mucho más ordenado como si tenemos un armario sin cajones en casa y ponemos toda la
00:10:27
ropa y a granel o de repente tenemos cajoneras y perchas y las chaquetas y los abrigos los ponemos
00:10:34
en las perchas y la ropa interior y los calcetines en unos cajones separados.
00:10:39
Entonces todo está como más organizadito.
00:10:43
Además nos resulta útil los paquetes no solo por tener un cierto orden
00:10:47
que cuando vayamos a hacer un mantenimiento es más fácil localizar las zonas de código.
00:10:52
Si tenemos un error de repente o tenemos que hacer una actualización
00:10:57
en el software de recursos humanos, pues seguramente si lo tenemos en un paquete
00:11:00
que sea recursos humanos, la actualización la vamos a tener que hacer en código
00:11:04
que cuelga de ahí. Y si ahí tenemos 10 ficheros, pues sabemos que tendremos que tocar en esos 10 ficheros.
00:11:08
No va a resultar más fácil hacer un análisis y un desarrollo nuevo para actualizarlo que si esos 10 ficheros
00:11:13
los tenemos mezclados con otros 200 del resto de funcionalidades que pudiera tener el banco.
00:11:19
Y una tercera ventaja que se me ocurre es que imaginaros que hemos hecho para un determinado banco un desarrollo
00:11:26
y nos funciona todo, lo tenemos muy bien probadito,
00:11:33
estamos muy contentos con ese software
00:11:37
y de repente nos contrata otro banco,
00:11:38
nos pide su desarrollo, pero bueno,
00:11:41
para ciertas funcionalidades no le interesa nuestro código
00:11:42
porque es muy particular para el desarrollo anterior,
00:11:46
pero en cambio la parte de recursos humanos
00:11:49
es que está clavada como ellos también la querrían.
00:11:51
Pues bueno, resulta muy sencillo coger
00:11:54
el paquete de recursos humanos tal cual
00:11:56
y portar de un proyecto a otro ese paquete.
00:11:59
Entonces, directamente no necesitamos andar entre todo el código intentando localizar qué trocitos de código cogeríamos de un sitio o de otro para obtener esa misma funcionalidad en el segundo error. Esto un poco en cuanto al nivel funcional de los paquetes y un poquito en cómo Eclipse organiza esos paquetes en el sistema de archivos.
00:12:02
paquete de recursos humanos que pudiera ser el paquete 1 pues fijaros tiene un directorio que
00:12:25
me interesa para otro proyecto cojo este directorio con todo su contenido interno y traslado este
00:12:30
directorio al segundo de los proyectos mirad aquí en el paquete aquí en el paquete 1 vamos a crear
00:12:35
una nueva clase que la vamos a llamar vamos a llamarle clase clase 1 del paquete 1 fijaros
00:12:43
que por el hecho de pertenecer al paquete 1 esta clase pone en la cabecera la etiqueta
00:13:00
package identifica en qué paquete se encuentra vamos a crear una segunda clase aquí bueno por
00:13:07
seguir un poco con la misma nomenclatura se llamaría clase 2 del paquete 1 y aquí en el
00:13:17
paquete 2 vamos a crear otra clase más que sería la clase 1 del paquete 2
00:13:27
Y ahora vamos a crear ciertas variables para intentar, digamos, justificar los ámbitos que nos dice la teoría respecto a las etiquetas public, protected, si no está especificado que sería ámbito de paquete o private.
00:13:36
Entonces, si venimos, por ejemplo, aquí a la clase 1 del paquete 1, aquí vamos a definir cuatro variables, una que sea una variable public, da igual el tipo, para ver el ámbito en sí, bueno, pues el tipo que sea sería indiferente, tendrá sentido que sea un enter, un string o lo que sea, en función de la información que pueda recoger, pero para ver el ámbito de alcance, lo que nos fijamos es en esta etiqueta anterior, con lo cual, bueno, es indiferente utilizar un tipo de variable public.
00:13:56
o otro entonces vamos a poner y entero público este pub como hemos definido aquí la variable
00:14:26
de tipo público para saber manejarla vamos a definir una que sea mantener esta pública
00:14:42
vamos a poner esta como private de la variable la podríamos llamar priv tenemos la privada vamos
00:14:50
a definir una que sea protegida, protective, y vamos a definir una que no tenga definición
00:15:02
ninguna. Estas variables, si no se pone por defecto ninguna, tienen alcance package. Creo
00:15:25
que recordar que se podría definir como package de forma explícita. Bueno, dice que lo borremos.
00:15:34
bueno si no lo ponemos ninguna la de por defecto es de alcance package o también no sé si en esta
00:15:43
en nuestra teoría pero hay ciertos sitios donde la llaman también friendly de amigable friendly
00:15:49
o package son este tipo de variables bueno le gusta la etiqueta package si no ponemos nada
00:15:56
son la frente o package y vamos a ver los diferentes alcances que tiene esta public
00:16:09
protective me falta la private ahora de fijaros en esta clase hemos definido cuatro atributos una de
00:16:20
cada tipo las las variables que son privadas están variables o métodos esto esto es equivalente para
00:16:37
métodos y variables que en los cuales definamos estas etiquetas tienen su alcance dentro de la
00:16:48
propia clásica única única y exclusivamente de si nosotros cogemos bueno dentro de un método en la
00:16:53
misma clase vamos a definir que un método vamos a poner un método public void mi método permite
00:17:01
acceso a cualquier variable dentro de la clase las que tienen un acceso más restringido son las
00:17:14
privadas que solamente estarán disponibles dentro de la clase propia donde están definidas pero
00:17:19
cualquier otra también está disponible. Es decir, dentro de la misma clase, cualquier variable
00:17:24
está al alcance. De hecho, fijaros cómo
00:17:29
vamos a poner un valor aquí. Dentro de un método
00:17:32
que pertenezca a la clase donde están definidas, cualquiera
00:17:54
de las etiquetas están disponibles. Es el ámbito más cercano, parece que
00:17:59
tiene sentido. Una variable que no estuviera disponible dentro de la misma clase
00:18:03
no tendría en realidad ninguna utilidad. Si nos vamos
00:18:06
a una clase que esté en el mismo paquete la clase 2 del paquete 1 pues podríamos venir aquí y definir
00:18:15
un objeto de esa clase entonces decimos clase 1 en la clase 1 recordad que es donde hemos definido
00:18:23
estas cuatro variables que son las que vamos a ir haciendo comprobaciones en función de la etiqueta
00:18:32
Vamos a definir un objeto de esta clase aquí dentro. Clase1, mi objeto de clase1 igual a new clase1.
00:18:37
Entonces si yo ahora cojo aquí, voy a hacer un copy para no tener que escribir tanto, defino un método, public void mi método y ahí intento acceder a los atributos de esta clase, vamos a ver a cuáles me deja y a cuáles no.
00:18:52
mirad, en una segunda clase, la clase 2
00:19:28
que está en el mismo paquete que la clase 1
00:19:38
pero es una clase distinta, clase 1 que tiene las 4 variables
00:19:42
y clase 2 que está en el mismo paquete que la clase 1
00:19:47
podríamos acceder a cualquier tipo de variable, a la pública, a la protegida
00:19:50
y a la paquete, pero no podríamos a la privada
00:19:55
es decir, la privada no podemos
00:19:58
en una clase, aunque comparta el mismo paquete.
00:20:00
Al resto sí.
00:20:10
En una clase propia tenemos acceso, sea cual sea la etiqueta.
00:20:11
Si queremos que el acceso a una determinada variable
00:20:15
no esté disponible en ninguna otra clase,
00:20:19
esté donde esté del proyecto, la definimos como privada
00:20:21
y ya no tendrá nunca acceso desde ningún sitio,
00:20:24
nada más que desde la propia clase.
00:20:29
Vamos a ponernos en situaciones.
00:20:32
Imaginaos que es una persona, está la clase persona, tenemos un getter y un setter que luego los volvemos a repasar para asignarle una edad y en mi proyecto esa edad va de 0 a 100 años para la persona o a 200 años, de 0 a 200 años.
00:20:35
Vamos a darle un poquito más margen de los 100. Si nosotros queremos tener certeza que la variable edad, que sería la equivalente a esta, no se modifica fuera de la clase persona que estoy programando yo en ningún otro sitio del proyecto y creo yo un getter y un setter para modificar ese valor haciendo un control de que la edad no sea ni mayor ni menor de 0 ni mayor de 200.
00:20:53
Si no me fío, no me fío entre comillas, ¿vale? Porque el proyecto lo está realizando mucha gente y a lo mejor incluso dentro de mi paquete este, una clase diferente la puede programar otra persona, no quiero que tengan acceso directamente, pues la pondría privada.
00:21:18
si al contrario de esto todo el paquete 1 por ejemplo lo voy a desarrollar yo y bueno pues no
00:21:33
me importa que modificar la edad de forma directa desde otras clases diferentes pero sólo desde mi
00:21:43
paquete porque este otro paquete sí que lo está desarrollando otra gente y no tengo la certeza de
00:21:50
que vaya a tener esa precaución de no darle una edad menor de 0 ni mayor de 200 pues podría
00:21:54
utilizar tendría que utilizar una etiqueta diferente de privada que me dé acceso en todo
00:22:00
el paquete por ejemplo no ponerla que me da acceso a todo el paquete pero con la package me da acceso
00:22:05
dentro de todo el paquete pero no en otros paquetes que pudiera tener el proyecto privada que está
00:22:11
privado que está pensado para el acceso desde solamente esta clase ya incluso desde una clase
00:22:18
diferente pero incluso dentro del mismo paquete ya no me lo permite ya no compila y vamos a hacer
00:22:23
esta misma jugada pero nos vamos a venir a la clase del paquete 2 a ver privada lógicamente no
00:22:33
me va a dejar porque ya está encerrado simplemente a esta clase pero todavía va a tener alguna
00:22:42
restricción más al paquete 2 al ya que la clase paquete 2 no pertenece a la misma clase que la
00:22:46
clase 2 de que la clase 1 del paquete 1 donde tenemos definidas las variables entonces si nos
00:22:52
venimos por aquí, si intentamos poner, fijaros, voy a definir un objeto de esta clase aquí, entonces me vengo por aquí y yo digo mi objeto 1, vamos a poner aquí, igual a new y no me compila, ¿por qué no me compila?
00:22:58
porque para que esta clase esté disponible dentro de este para que la clase 1 del paquete 1 esté
00:23:21
disponible dentro de la clase 1 del paquete 2 es necesario importarla al no pertenecer al
00:23:30
mismo paquete aquí no había sido necesaria necesario hacerlo porque ambas clases tanto
00:23:35
ésta como ésta pertenecían al mismo paquete entonces no es necesario importarlo ya lo estamos
00:23:42
indicando aquí que pertenece al paquete 1. En cambio, en este caso, como la clase 1 del paquete 2
00:23:48
es una clase que está en un paquete diferente a la clase donde están las variables,
00:23:55
si intento instanciar un objeto de ella, es necesario hacer un import.
00:24:00
Algo parecido a lo que nos sucede cuando importamos para escáner algunas librerías de las que están en Eclipse.
00:24:04
Eclipse nos ayuda un poquito aquí, nos dice importalo, vamos a ponerlo aquí directamente,
00:24:13
Ella me dice importamos desde el paquete 1 la clase 1 y entonces ya está disponible dentro de esta clase que está en el paquete 2 y ya podemos instanciar un objeto.
00:24:17
Entonces si ahora nos venimos y hacemos un copy y pega de esto, cambiamos el nombre, lo hemos llamado de forma diferente, fijaros que en una clase que se encuentra en otro paquete diferente, lo único que está disponible en principio es la variable que hemos definido como pública.
00:24:34
Ni la protected, ni la package por defecto, ni la privada.
00:25:12
Aquí ya no me deja.
00:25:22
Si definimos una clase como, fijaros, el resto, en realidad,
00:25:28
bueno, pues tienen que ver un poquito con, bueno,
00:25:37
la package está muy identificada al propio paquete donde nos encontramos.
00:25:39
La privada está directamente relacionada con la clase donde está definida. Las públicas están disponibles en cualquier sitio del proyecto, me da igual, donde esté, en un paquete, en otro, con unas condiciones o con otras.
00:25:44
Y luego tenemos el tema de las subclases. Os cuento cómo va esto. Una de las características de la programación orientada a objetos es la herencia.
00:26:02
mira si yo cojo y vamos a definir otra incluso aquí aunque esté en otro
00:26:14
para que otro paquete diferente voy a comentar esto para que compile vamos a
00:26:25
definir una clase que sea que herede de otra
00:26:33
y ahora os cuento para qué sirve la herencia yo creo ya lo hemos hablado en
00:26:37
algún momento vamos a definir aquí dentro del paquete 1 incluso una clase
00:26:41
esta clase pertenece al paquete 2 y podrá tener sus parámetros y sus atributos propios cuando
00:26:48
cuando estamos definiendo la característica de herencia lo veremos también en el siguiente tema
00:27:01
y damos otra vuelta justo a este concepto lo que hacemos es que una determinada clase coge
00:27:04
características de otra que digamos tiene un rango más más cerrado imaginaos que tenemos en un pro en
00:27:11
un programa la clase alumno y la clase profesor. Tanto los alumnos como los profesores, si definimos
00:27:19
dos clases por separado, porque es lo que nos está demandando el ejercicio, ambos dos tendrán
00:27:26
un nombre y ambos dos tendrán una edad. En cambio, el alumno tendrá un número de matrícula y el
00:27:31
profesor tendrá un número de taquilla, si los profesores tienen taquilla. Los alumnos no tienen
00:27:38
taquilla los profesores no tienen número de matrícula. Cuando estamos definiendo cada una
00:27:44
de esas dos clases, si esto fuese la clase alumno, pues pondríamos aquí private o como sea,
00:27:50
con el ámbito que nos interese, int, string, ese nombre, si lo hacemos private estaría solamente
00:27:58
accesible desde la propia clase, estas variables, int y edad, y por ejemplo tendríamos private, int y num matrícula.
00:28:09
Si esta es la clase alumno, pues tendríamos estos tres parámetros. En la clase profesor, que tendríamos en otro
00:28:23
ficherito, probablemente estos dos nombres volverían a existir y este no existiría, en cambio existiría el del
00:28:29
número de taquilla en lugar de número de más. ¿Qué sucede? Que estos dos son comunes.
00:28:37
Una forma de implementar esto, lo que podríamos hacer es definir
00:28:43
una clase que sea persona y todas las
00:28:46
personas, tanto si finalmente termina siendo un alumno o termina siendo
00:28:51
un profesor, tendrán un nombre y una edad. Con lo cual estos dos parámetros los
00:28:55
podríamos poner atributos, los podríamos poner en la clase
00:28:58
persona. Este no lo podríamos poner en la clase persona porque solamente lo tendrían
00:29:02
aquellas personas que terminen siendo alumnos. De la misma forma que el número de taquilla no
00:29:06
podríamos poner en la clase persona porque solamente lo terminarían teniendo aquellos
00:29:12
que sean profesores, pero estos dos sí que lo tienen disponibles. Entonces estos dos los
00:29:16
podríamos derivar a la clase persona y cuando estamos definiendo la clase alumno, aquí lo he
00:29:22
llamado clase herencia, lo que podríamos hacer es definir en esta misma clase única y exclusivamente
00:29:29
el número de matrícula y aquí decir que hereda Stance, en la etiqueta que se utiliza en Java para hablar de la herencia, Stance de la clase, en aquí pondríamos de la clase persona, que la tendríamos definida con los atributos de nombre y edad.
00:29:35
en particular como la clase personal no existe en este proyecto
00:29:55
pues podríamos decir que hereda de la clase
00:29:59
clase 1, ¿por qué no le gusta esto?
00:30:02
pues porque no reconoce esta clase
00:30:09
fijaros que la clase herencia la hemos definido en el paquete 2
00:30:12
nos vuelve a pasar lo mismo que aquí, necesitamos importarla
00:30:15
para que la reconozca, entonces
00:30:18
en el ejemplo este ahora vemos a nivel
00:30:23
práctico con el desarrollo que estamos haciendo
00:30:26
la clase herencia tendría este atributo
00:30:30
el número de matrícula y la clase alumno, por heredar de la clase persona, en el ejemplo que estábamos hablando, también tendría el nombre y tendría la edad.
00:30:32
En particular, ¿qué atributos tiene aparte de esta clase herencia al heredar de clase 1P1? Pues tiene estos. Esos cuatro los tiene heredados.
00:30:44
Ahora, ¿va a poder acceder a todos ellos según la etiqueta que tengamos aquí? Pues vamos a comprobar. ¿Se entiende un poco el concepto de herencia?
00:30:59
En el tema siguiente creo que es, volvemos a hablar de él, si no ahora después lo repasamos un poquito más.
00:31:08
Entonces si nos venimos y hacemos copy-paste de un método de este tipo, ahora necesitamos instanciar un objeto porque realmente él tiene ya estos parámetros heredados.
00:31:16
Fijaros cómo nos cambia el ámbito de acceso respecto a la clase 1-2.
00:31:46
De partida, la clase 1, P2 y la clase herencia, ambos dos están definidos en el paquete 2 y estamos intentando acceder a atributos, estos cuatro, que están definidos en una clase del paquete 1.
00:31:55
En una clase normal del paquete 2, la única etiqueta que permite que estén accesibles sus atributos son las públicas, ¿veis? Ni la protectiz, ni la paques, ni la privada.
00:32:14
están accesibles. En cambio, si resulta
00:32:28
que la clase es hija de la clase
00:32:32
de la cual va a utilizar los atributos, están disponibles
00:32:36
tanto los públicos como los protective. Ahí es la diferencia entre
00:32:39
si es una clase hija de donde está definido el parámetro
00:32:43
o una clase donde no está definido el parámetro, la protective.
00:32:48
Y no sé si con esto tenemos ya toda la casuística de las etiquetas.
00:32:56
Mira, si hacemos una tabla más o menos, podríamos decir public, protected, no especificado, que sería el package, o friendly, y la private, que vienen a ser estas cuatro que tenemos definidas en el ejercicio.
00:32:59
Las publicas, ¿dónde están accesibles? Están accesibles desde cualquier clase en todo el proyecto.
00:33:22
Las packets, yo creo que estas dos son como más entendibles,
00:33:37
porque si es packets o no he dicho nada, pues está claro que es desde el paquete.
00:33:44
Entonces estas están accesibles desde su mismo paquete.
00:33:48
Fijaros cómo aquí la packets no está, esta clase pertenece a un paquete diferente
00:33:56
donde están definidas, en la clase herencia la packets tampoco está,
00:34:10
en la clase 1 que es la misma clase, la clase Package está
00:34:14
y en la clase 2, perdón, clase 2 del paquete 1
00:34:19
la Package está disponible porque pertenece al mismo paquete donde está definida
00:34:26
y en su misma clase también lo está. La pública
00:34:30
que es esta otra que hemos indicado aquí
00:34:33
que está accesible desde cualquier sitio
00:34:36
vamos a verificarlo, accesible desde la misma clase
00:34:42
donde está definida, accesible desde otra clase en el mismo paquete, aquí lo tenéis, en otro paquete
00:34:46
también está accesible, da igual que sea una clase que hereda o que no hereda. La protective lo que
00:34:54
tiene es que está disponible en el propio paquete y también está disponible si es una clase hija de
00:35:07
donde está definida. Mirad, la clase herencia acepta la protective. ¿Por qué la clase herencia
00:35:29
si le vale el acceso a la variable de tipo protective? Porque la clase herencia es hija
00:35:39
de la clase donde está definida esa variable. En cambio, si nos vamos aquí a clase 1 del paquete 2,
00:35:45
está en un paquete diferente, pero fijaros como no es hija, no tiene el extens, la protective
00:35:53
tampoco está disponible. Y luego la tercera etiqueta que nos queda es la privada, que esta me da igual herencia,
00:35:59
me da igual cualquier cosa, está solo accesible en la propia clase, la privada. Y si nos venimos por aquí,
00:36:09
fijaros como aquí la privada está accesible, que es justo la clase donde está definida, privada,
00:36:23
pero ya no vayamos donde no vayamos, incluso teniendo en consideración
00:36:28
que puede ser una clase del mismo paquete, la privada ya no compila
00:36:33
aquí la privada no compila
00:36:37
y aquí la privada, a pesar de que es una clase
00:36:40
hija de esta otra, sigue sin compilar
00:36:45
y estas etiquetas que definimos como público-privada
00:36:49
sin etiqueta, o sea, público-protegida sin etiqueta
00:36:54
para que sea package o friendly o private estas más etiquetas son aplicables a los métodos los
00:36:58
métodos están accesibles en el mismo ámbito que los que los para que los atributos según
00:37:05
la etiqueta está que pongamos en unas y otras clases si se entiende más o menos seguís por
00:37:10
ahí verdad vale vale pues bien una vez visto que bueno que esto nos permite gestionar hasta
00:37:27
donde queremos que estén accesibles nuestras variables, puede resultar que el hecho de que no estén accesibles
00:37:37
no sea porque no queramos que se modifique esta variable, sino que puede ser porque queremos tener un control
00:37:45
sobre cómo se modifican estas variables, lo que os hablaba antes de la edad.
00:37:52
Vamos a poner aquí un private, int y edad.
00:37:57
Resulta que la edad, si esto fuese la clase persona, igual tenía que haber utilizado otros nombres desde el principio,
00:38:03
que fuesen estos pero bueno tampoco importa mucho la edad quiero que vaya entre 0 y 200 años yo lo
00:38:09
pongo privado porque yo está esta clase la estoy programando yo y yo voy aquí voy a tener mucha
00:38:17
precaución de que esta variable nunca tenga un valor diferente de entre 0 y 200 si os resulta
00:38:21
que yo esto lo dejo como público cuando lo estoy definiendo yo puedo decir esta variable tiene que
00:38:29
entre 0 y 200 pero el momento que yo he hecho esto público igual en esta zona de código que
00:38:38
no estoy con la que yo no estoy trabajando pues alguien me coge y me dice y 1.1 edad es igual a
00:38:48
300 y ya la mucha fao y tú tienes control si es otro grupo de trabajo el que está haciendo esto
00:39:01
Pues no. ¿Estás saltándote el requisito de que esta edad iba entre 0 y 200? Pues sí. Si yo cojo aquí y esto lo pongo como privado, como os decía, yo ahora me vengo aquí y ya no me permite hacer este cambio.
00:39:08
Directamente yo tengo un control, ya que toda modificación sobre ese atributo y edad se tiene que hacer por ser privado dentro de mi clase.
00:39:26
Sí, bueno, si me fío un poco más, porque a lo mejor está, imaginaos que el trabajo lo estamos haciendo entre dos empresas y digo el paquete uno me lo han contratado a mí y el paquete dos lo han contratado a otra empresa y digo, mira, seguramente sean unos créditos de la otra empresa, pero yo me fío de los de mi empresa y todo este desarrollo lo estamos haciendo diferentes personas, pero me fío que van a tener cuidado, pues entonces podría coger y definir aquí esto en lugar de private, definirlo como package.
00:39:33
desde mi paquete está accesible, pero desde este otro paquete que está en otra
00:39:59
empresa desarrollándolo, pues no lo está. Esto quiere decir
00:40:04
que si yo le defino esto como privado, este
00:40:09
atributo ya solamente es útil dentro de esta clase
00:40:12
y nunca nadie va a poder modificar la edad de esta
00:40:16
clase que estamos haciendo el supuesto que podría ser la clase persona, pues no,
00:40:20
porque la edad en realidad se puede modificar desde cualquier sitio del proyecto.
00:40:24
Pero para tener este control, lo pongo privado y ahora lo que hago yo es crearme unos métodos de acceso al atributo. ¿Y qué métodos de acceso son? Pues los que se llaman getters y setters, que también los hemos hablado ya en algún momento.
00:40:28
Entonces, para este atributo, por ejemplo, yo cojo y me hago, voy a utilizar la ayuda del IDE, digo, génerame los getters y los setters. Pues, ¿para quién? Me ofrece por aquí diferentes, pues, digo, para la edad. Get y edad, lo digo, géneramelos.
00:40:42
Y estos me los define como públicos. Es decir, a estos métodos sí que puedo acceder yo desde cualquier sitio. ¿Por qué? Porque tienen etiqueta pública. Fijaros como si yo me vengo aquí, digo mi oj1.set y edad.
00:40:57
¿Veis? Este sí me compila. ¿Por qué me compila el acceso a ese método? Pues porque lo he definido público. ¿Esta clase está en un paquete distinto? Sí. Lo público, habíamos dicho que estaba accesible desde cualquier sitio en todo el proyecto.
00:41:20
entonces yo aquí puedo coger y puedo modificar la edad
00:41:35
es cierto que yo puedo poner aquí un 300
00:41:37
que vendría a ser el equivalente de poner este 300 aquí
00:41:39
que no es válido
00:41:43
pero yo ahora aquí tengo
00:41:44
y este setter que me ha generado
00:41:47
de forma pragmática de Clisse
00:41:51
lo que hace es esta variable
00:41:53
que recibe como parámetro el método
00:41:55
se lo asigna a la misma variable
00:41:57
que tiene como atributo
00:42:00
el yedad este
00:42:02
Con lo cual, en este caso, estaría aplicándole el 300. Pero ahora resulta que este método está dentro de la clase que estoy yo programando. Aunque aquí sí que tiene la posibilidad abierta de meter un valor que esté en el rango de los enteros, 300 o un millón incluso, o 10 millones de años, sí que es cierto que para que llegue a este atributo tengo que asignárselo yo aquí.
00:42:03
¿qué podría hacer? pues en alguna ocasión ya lo hemos hecho, podríamos decir
00:42:26
sí, el valor, fijaros, aquí tengo yo el control para gestionar
00:42:31
que ese atributo tenga la información que a mí me interesa, si es menor que 0
00:42:35
pues lo que voy a hacer va a ser
00:42:39
asignar un 0, si le paso
00:42:43
una edad de menos 30 años, pues al final lo estoy fijando a 0
00:42:47
el shift, así la edad
00:42:51
aquí me fijo en el margen superior que habíamos dicho
00:42:55
si es mayor que 200, pues le voy a decir que mira, que tenga la edad de 200
00:42:59
y solamente en caso de que no sea ninguna de esas
00:43:04
es decir, que esté entre 0 y 200, pues entonces digo dis y edad
00:43:10
que sea igual a y edad. Aquí me ha asegurado
00:43:17
con este setter que
00:43:23
este atributo nunca va a tener un valor diferente
00:43:25
que no es que esté fuera del rango de 0 y 200 este método lo tengo bajo mi control porque soy
00:43:30
yo quien estoy haciendo la programación y ya garantizo que en todo el proyecto sí o sí si
00:43:37
alguien quiere asignar una edad como lo tiene que hacer a través del setter no se puede saltar esa
00:43:42
norma que teníamos definido el getter pues qué sentido te podría tener pues bueno lo que nos da
00:43:46
la posibilidad el getter es de no acceder de forma directa a la edad porque bueno porque igual interesa
00:43:56
hacer aquí una algoritmia antes
00:44:02
de devolver esa edad.
00:44:05
Que no interesa, pues pon un return y edad
00:44:06
directamente y me devuelve la edad.
00:44:08
Pero bueno, pensad, yo que sé,
00:44:11
por poner un contexto, pensad que
00:44:12
en mi empresa, como
00:44:14
queremos ganar clientes y queremos parecer
00:44:16
que somos todos muy jóvenes
00:44:18
y la lucidez de la juventud la tenemos
00:44:20
a tope, ¿no? Pues
00:44:23
si de repente nos preguntan por la edad,
00:44:24
pues podría resultar que, aunque seamos
00:44:26
un poco mentirosillos, nos gusta decir que
00:44:29
tenemos 5 años menos, ¿no?
00:44:30
pues aquí podríamos tener asignada la edad de verdad y cuando me llame ya a la edad directamente
00:44:32
no puedo acceder desde fuera de mi clase porque está privado lo tengo que hacer obligatoriamente
00:44:38
a través de un getter pues aquí podría coger y decir que lo que devuelvo es la edad que tengo
00:44:43
menos 5 entonces bueno pues al resto del mundo poco mentirosillos aquí pero bueno le estamos
00:44:48
diciendo que la edad que tenemos es siempre menor de 5 para que no quede muy feo si tenemos dos años
00:44:56
pues podríamos poner aquí que solamente que si vamos a poner aquí un int y edad aus y decir que
00:45:03
si y edad es mayor de 5 entonces y edad aus que sea igual a y edad else y edad menor 5 perdón
00:45:14
y si no que y edad aus sea igual a edad para evitar que me devuelva una edad menor que la
00:45:37
que menos de cero vamos que entonces me pillarían con la mentira que estoy intentando lanzar o sea
00:45:46
que aquí en el get era antes de hacer el return me da la posibilidad de implementar una cierta
00:45:52
algoritmia que tenga yo pensada pensado antes de devolver el valor que tenga esa variable
00:45:57
entonces estos son los getter y los setter
00:46:03
¿tienen sentido los getter y los setter para
00:46:06
las variables privadas? pues bueno lo tienen
00:46:10
en el caso en el que
00:46:13
queramos que se pueda modificar este valor fuera de mi clase
00:46:14
porque al haberla definido como privada no sería posible
00:46:19
¿tiene sentido un getter y un setter en el caso
00:46:22
de que sea por defecto
00:46:25
package of friendly? pues bueno también tiene
00:46:28
sentido, porque yo si es package
00:46:31
de todo el código que haya por aquí, por ejemplo
00:46:34
mi equipo de trabajo, pues me fío de que directamente modifiquen
00:46:37
este atributo asignándole un valor
00:46:40
pero como no me fío de que lo puedan hacer correctamente
00:46:43
desde otros equipos de trabajo, desde otros paquetes
00:46:46
pues entonces dejo el ámbito como
00:46:48
friendly package. Pero quiero
00:46:52
que en estos otros sitios se puedan modificar, pues sí, pues entonces
00:46:55
para que estos de estos otros paquetes sean capaces de modificar mi edad, pues hago un getter y un setter.
00:46:58
Bueno, pues esto sería el getter y el setter. También lo habíamos hablado en algún momento.
00:47:10
No sé si tenéis alguna duda que queréis consultarme del getter y el setter.
00:47:15
Si no, pues bueno, os cuento, os sigo contando más cosas.
00:47:24
Otra de las etiquetas que hemos utilizado ya en algún momento es la etiqueta final.
00:47:29
la etiqueta final
00:47:33
se puede utilizar en diferentes ámbitos
00:47:37
y esta etiqueta sí que tiene diferentes significados
00:47:42
dependiendo de donde la vayamos a utilizar
00:47:45
el sitio donde lo hemos utilizado
00:47:47
inicialmente ha sido
00:47:54
para atributos de clase
00:47:57
entonces si yo pongo aquí int
00:48:00
y IVA, digo que el IVA sea igual al 12%
00:48:02
por ejemplo, para el sector en el que yo trabajo, aquí estoy definiendo
00:48:09
una variable, en particular lo estoy definiendo
00:48:16
con ámbito package, indiferente, solamente mencionarlo
00:48:19
como hemos estado antes hablando de ello, vamos a ponerlo por ejemplo privado
00:48:24
con lo cual solo estaría accesible desde mi propia clase, desde cualquier método
00:48:27
de mi propia clase, y por ser una variable yo podría poner aquí
00:48:31
Y iba, si me interesa, que es una variable, pues que de 12 pase a valer 5. Y esto compila y va perfectamente. Si le añado la etiqueta final, lo que estoy haciendo es convertir esto que ha estado en una variable de tipo entero y de ámbito de alcance privado, lo estoy convirtiendo en una constante.
00:48:35
Entonces, como ahora es una constante, lo que estoy fijando es el valor 12 y ya es inamovible de este valor 12 en todo el proyecto. Con lo cual, fijaros, como ahora ya no me compila. Es decir, convertimos una variable en una constante.
00:48:59
Lo que sí que es cierto es que las constantes suelen aparecer en el código con todo mayúsculas. Bueno, suelen. Digamos que es un convenio ahí de acuerdo de, vamos a poner las constantes con mayúsculas para que si vemos una palabra IVA aplicado, por ejemplo.
00:49:13
pues ahí va aplicado a aparecer así esto que no lo que nos permite pues que si de repente aparece
00:49:32
un iva aplicado por ahí en alguna parte del código vemos que todo es mayúsculas nos hace ya ir
00:49:39
teniendo una idea de que se trata de una constante a cambiarle el valor como es una constante no lo
00:49:44
permite pero si utilizarlo por ejemplo podríamos utilizarlo para sacar su valor para lectura no
00:49:51
para modificación pero sí para lectura lectura y escribirlo por pantalla aquí sí que me compré
00:49:59
le iba bien. ¿Sí? ¿Sí?
00:50:05
¿No me oís?
00:50:10
Buenas tardes. Ah,
00:50:12
vale, bien, bien. No, como decías se escucha,
00:50:14
pensaba que me decías que no se me escuchaba. Sí, se me
00:50:16
escucha bien, ¿no? Ah, sí, dime,
00:50:18
dime. ¿Los atributos?
00:50:20
Sí.
00:50:36
Claro, sí.
00:50:48
Sí, sí, sí, sí, perfectamente.
00:50:50
Bueno, el
00:50:52
hecho de definirlo como privado
00:50:53
permite que solamente
00:50:56
lo puedas acceder desde tu clase, correcto,
00:50:58
como bien decías. Pero a lo mejor
00:51:00
funcionalmente sí que quieres cambiar ese valor tú, como la edad que hablábamos antes, desde otras partes
00:51:02
del código. Lo que no quieres es que mediante código lo puedan cambiar. A ver, funcionalmente queremos
00:51:08
que exista la posibilidad de cambiar la edad, que una persona tenga una determinada edad y se le aplique
00:51:16
desde este código, pero que no se pueda acceder directamente a la variable Java que está definida
00:51:22
como privada. Y para eso es para lo que hacemos, utilizamos los getter
00:51:28
y los setters. Como lo hemos definido de forma privada, digamos
00:51:32
que técnicamente no está accesible desde aquí, desde este
00:51:36
código, pero funcionalmente conseguimos poder modificar
00:51:40
este valor a través del setter. Y en el setter, como
00:51:44
metemos, podríamos decir, pues si quieres
00:51:48
que esté accesible su modificación desde esta clase, pues directamente
00:51:52
ponla pública, ¿no? Podría ser
00:51:56
la pregunta que nos planteásemos.
00:51:58
Claro,
00:52:01
claro, es que en realidad
00:52:07
funcionalmente sí que quiero modificarla
00:52:08
desde otro sitio, pero quiero
00:52:10
acceder a ella teniendo
00:52:12
yo el control de cómo se modifica.
00:52:14
Como en este ejemplo hemos puesto
00:52:16
que la edad vaya entre
00:52:18
0 y 200 años, si yo esto
00:52:20
lo pongo público,
00:52:22
desde aquí yo podría poner
00:52:24
y edad y decir
00:52:26
que tenga un millón de años.
00:52:30
¿Por qué? Porque la única condición que me haría que esto no compilase sería el rango de valores que tiene un entero.
00:52:32
Entonces, podría ser que esta zona de código no la estuviera desarrollando yo, por ejemplo.
00:52:39
Entonces, alguien que está desarrollando esta zona de código podría poner este valor a la edad,
00:52:45
sabiendo que estamos incumpliendo un requisito de las edades que pueden tener las personas que participan en este programa,
00:52:51
que es que vaya entre 0 y 200.
00:52:56
¿Cómo evito yo que una persona ajena al código que estoy desarrollando yo
00:52:59
nunca pueda meter un valor entre 0 y 200?
00:53:04
Pues le digo, mira, aunque la edad funcionalmente
00:53:07
voy a permitirte que la modifiques entre 0 y 200,
00:53:10
no te voy a dar acceso directo a esta variable de tipo entero.
00:53:13
Y eso lo hago poniéndolo esto como privado.
00:53:17
Y sí que te permito modificar este parámetro,
00:53:21
pero te obligo a que lo hagas a través de la llamada un método.
00:53:23
este método lo defino público que sí que está alcanzable
00:53:27
es alcanzable desde aquí y ya pongas lo que pongas
00:53:32
como yo aquí pongo cierto código que me controla que el valor
00:53:36
no sea nunca mayor de 0 y 200 garantizo que esta variable
00:53:40
accesible desde todo el programa a través de
00:53:44
funcionalmente accesible a través del set y edad tenga este
00:53:47
rango y garantizo que esta variable directamente nadie
00:53:52
me la va a modificar a no ser que sea a través de este método del setter bueno si podría podríamos
00:53:56
llamarlo un encriptado sí o sea digamos que sí sí sí mira mira ya verás mira tú imagínate que
00:54:04
a una persona yo cojo y le digo quiero aplicarle la edad de 50 por digo y edad si pongo y edad
00:54:20
igual a 50 no me compila porque porque la tengo definida como privada esto me asegura que no soy
00:54:29
capaz de poner un millón porque como no puedo hacer allá directamente mira si yo pongo aquí
00:54:41
set y edad como se llama el setter bajamos un segundito aquí set y edad incluso una edad que
00:54:46
no vale, voy a asignarle a esa persona 500 y luego aquí
00:55:03
un system.out.println
00:55:07
y aquí hago un get
00:55:12
y edad, aquí cojo el valor que tiene la variable
00:55:15
y la muestro a través de system.out.println y previamente
00:55:19
he asignado una edad de 500, bueno esto tendría que estar
00:55:23
en un main para que nos permita ejecutarlo
00:55:27
public static voice main
00:55:30
bueno, ahora ha dejado de compilarme
00:55:38
porque estoy intentando acceder
00:56:00
a través del main a una variable
00:56:02
el main es static, estoy intentando acceder
00:56:05
a métodos que no son static
00:56:09
entonces aquí vamos a necesitar definir una variable
00:56:11
de ese tipo, ahora retomamos tu pregunta
00:56:15
si no
00:56:21
si no te queda claro mira vamos a poner en lugar de a ver uno mira aquí estamos dando de alta ahora
00:56:22
a ver si somos capaces de ejecutar el programa desde aquí estamos dando de alta bueno llamó
00:56:51
clase 1 vamos a suponer que es una la clase persona vale una determinada persona hacemos
00:56:58
su new y podemos coger y decir mira ahora mismo muéstrame a ver qué edad tiene esa persona aquí
00:57:04
es previsible que salga a cero porque es un entero inicialmente su valor es cero mira vamos a poner
00:57:13
aquí vamos a poner tres casos vamos a ponerle que tenga una edad de 20 aquí es previsible que salga
00:57:20
20 y ahora intentamos asignar una edad de 500 y aquí es previsible ahora lo ejecutamos a ver si
00:57:29
de verdad es así, que salga
00:57:38
200, no
00:57:40
500, ¿por qué no 500?
00:57:42
Porque este
00:57:45
set y edad
00:57:45
lo hemos bloqueado aquí, ¿ves?
00:57:48
Estamos modificando la edad
00:57:51
en el fondo, pero gracias
00:57:52
a no permitir que
00:57:54
se acceda directamente a la edad
00:57:56
por ser privada, estamos
00:57:58
garantizando que a través de este setter
00:58:00
nunca nos puedan meter que la persona
00:58:02
tiene un millón de años,
00:58:04
desde una zona de código que es
00:58:06
que está en un paquete diferente a donde tengo ya definida la supuesta
00:58:08
clase persona, que es donde tengo identificado el atributo
00:58:13
y edad. Entonces, mira, si yo cojo
00:58:17
a ver si soy capaz de ejecutarlo desde aquí, voy a darle
00:58:20
a ejecutar por aquí, no sé si me... run as, por aquí
00:58:24
java application, mira. Bueno, resulta que con el
00:58:34
getter me estás mostrando, ¿os acordáis que habíamos dicho que pusiera 5 de menos?
00:58:41
bueno, me está mostrando menos 5, esto habíamos intentado evitarlo, ahora si queréis
00:58:45
reemplazamos el getter, aquí 10 y aquí 190
00:58:48
¿por qué aquí tiene restado 10? porque en cada una de las veces con el getter estamos
00:58:52
restándole 5, no, no, no estamos llamando al atributo, estamos llamando
00:58:56
a estos métodos, al set y edad
00:59:16
y al get y edad, no, bueno, si estás trabajando
00:59:20
aquí, aquí estás asignando edades y modificándolas
00:59:34
voy a quitar un momentito esto para que no nos confunda
00:59:37
voy a decir que devuelva la edad exactamente
00:59:41
pero tú funcionalmente sí que estás trabajando
00:59:46
con la edad de la persona
00:59:51
mira
00:59:55
tú imagínate que tienes
01:00:05
en esta zona de código tú quieres modificar la edad de una persona
01:00:07
y quieres leer su edad
01:00:12
¿estás modificándola aquí?
01:00:14
¿con este set? ¿estás modificando la edad?
01:00:18
Mira, si ejecutamos, claro, pues entonces sí que puedes, funcionalmente sí puedes modificar la edad de la persona. Lo que no puede, no, porque es privada, pero el servicio de dar edades y de recuperarlas, funcionalmente lo tienes.
01:00:20
¿Por qué? Porque puedes dar edades a través de set y edad y puedes leerlas a través de get y edad. Entonces, funcionalmente sí que tienes ahí un acceso a una variable entero que está reflejando la edad de la persona.
01:00:52
Lo que te estás garantizando es evitar, porque es uno de los requisitos que tiene tu programa, el hacer que la edad valga más de 200 o menos de cero, de forma inadecuada.
01:01:04
Es decir, tú das un servicio, mira, bueno, no a mala leche, por equivocación, ¿sabes? A lo mejor, yo que sé, alguien nos ha leído los requisitos de que esa variable no pueda, mira, permíteme, sí, claro, por cerrar, mira, sí, por cerrar un poco te voy a hacer una analogía de estas con un ejemplo que a veces pongo, que a veces, pues a lo mejor pueden parecer un poco tontos,
01:01:26
Imagínate que tú estás en una frutería y resulta que no tienen guantes de plástico para dejarnos a todos para coger las frutas.
01:01:58
Tú quieres comprar una manzana y puede ser que te digan, mira, si llegas a la frutería yo no te dejo que toques la manzana. Para coger la manzana se la tienes que pedir al cajero, que él sí que tiene unos guantes, te coge la manzana y te la da.
01:02:07
Pero está prohibido que tú cojas la manzana con tus manos.
01:02:23
¿Cuando salgas de la frutería te vas a llevar una manzana a casa que es funcionalmente lo que quieres?
01:02:28
Sí.
01:02:33
¿Has bloqueado de alguna forma que todo el mundo llegue y toque la manzana con la mano?
01:02:34
La ha bloqueado con esa norma.
01:02:39
Pues es un poco esto, para evitar que la edad la toquemos con la mano como la manzana,
01:02:42
es decir, que asignemos un valor que sea menor o mayor de 200,
01:02:47
asegurarnos que quien toca la manzana
01:02:51
tiene puestos los guantes, es decir, lleva la edad
01:02:53
un valor entre 0 y 200, no te permito
01:02:56
que toques directamente la manzana, no te permito que modifiques
01:02:59
directamente la edad, para hacerlo tienes que
01:03:02
pero vas a poder llevarte una manzana a casa, sí
01:03:06
vas a poder consultar la edad, sí, vas a poder actualizarla
01:03:08
sí, pero tendrás que hacerlo a través de los setters y los getters
01:03:12
que es pedirle al dependiente
01:03:15
oye, cógeme tú la manzana que eres el único que tiene los guantes
01:03:17
es un poco la idea
01:03:20
no sé si la equivalencia
01:03:23
un poco aclara algo
01:03:26
o hace que se entienda
01:03:28
directamente no
01:03:28
pero no puedes
01:03:34
pero es tu decisión de diseño
01:03:36
cuando estás implementando esta clase
01:03:37
esta etiqueta la pones tú
01:03:41
entonces si tú lo que quieres es
01:03:42
que la manzana siempre se coja con guantes
01:03:45
desde alguien que sea ajeno
01:03:47
aquí a la clase
01:03:49
es decir, que nadie pueda modificar el valor de la edad
01:03:50
desde alguien que sea ajeno a la clase, pues le pones privado.
01:03:53
Si te fías porque todos los que trabajan en tu tienda,
01:03:57
que son los que pertenecen a tu propio paquete,
01:04:01
se lavan las manos antes de pasar a trabajar y te fías de ellos,
01:04:04
pues puedes definirlo esto como package,
01:04:08
porque de todos los que trabajan en esta zona,
01:04:10
yo me fío para que modifiquen directamente este valor,
01:04:12
porque todos conocen que ese valor no puede ir más allá de 200
01:04:16
ni menor de cero.
01:04:20
y si no te fías de los de tu
01:04:21
de los de tu tienda, porque dices
01:04:23
es que algunos no se lavan las manos por la de fines
01:04:25
privada para solamente hacerlo tú
01:04:27
y si te fías de todo el mundo, dices, pues bueno
01:04:29
es que no es una manzana total
01:04:31
son unas tijeras
01:04:33
pues ya está, que eso me da un poquito más igual
01:04:36
pues entonces la de fines pública y todo el mundo
01:04:38
llega y directamente compra las tijeras
01:04:40
¿sí? vale
01:04:42
bueno, pues esto era, sí
01:04:45
vale, pues nada
01:04:46
retomamos, continuamos con el
01:04:49
tema de lo de final, final para los atributos lo convierte en una constante, como hemos hecho con,
01:04:51
no me acuerdo en qué clase ha sido, por aquí, esta final. Cuando la etiqueta final está identificada
01:05:00
en una clase, lo que no permite es que esa clase tenga hijos. Esto está relacionado de nuevo con
01:05:10
la herencia. ¿Os acordáis aquí que hemos hablado un poquito de la herencia? La herencia, repasaremos
01:05:17
esto y volveremos a hablar de ello en otra tutoría cuando cuando lo veamos formalmente pero bueno
01:05:23
para explicar la etiqueta final es necesario relacionado con una clase fijaros hemos dicho
01:05:30
que la clase herencia es hija de la clase 1p1 y el hecho de que sea hija implica que tiene
01:05:37
disponibles los atributos que tiene esta clase y tiene disponibles los métodos que tiene esta clase
01:05:47
también luego podrá acceder a ellos si no son privados cuidados y son privados por mucho que
01:05:55
sea una clase hija no poder no tendría acceso a ellos pues mirad cuando una clase la ponen a una
01:06:01
clase ponemos la etiqueta final este final lo que significa es que es una clase que ya no admite
01:06:09
herencias, es decir, si tenemos un
01:06:16
árbol de herencias, este fuese la clase
01:06:19
persona, de la clase
01:06:20
persona ya no sería posible
01:06:23
hacer que hereden
01:06:24
nuevos hijos. ¿Os acordáis? Antes decíamos
01:06:26
esta es la clase alumno
01:06:29
que hereda de la clase persona.
01:06:30
La clase alumno tiene sus características
01:06:33
y por herencia
01:06:34
los atributos
01:06:36
y métodos de la clase persona.
01:06:39
Hay una posibilidad
01:06:42
cuando tú estás implementando
01:06:43
una clase, es decir,
01:06:45
Este es el punto final en un posible árbol de herencias.
01:06:46
Ya de esta clase no hay clase que herede.
01:06:50
Imaginaos que está la clase persona y decimos, si alguien quiere implementar una clase alumno,
01:06:53
que la implemente de forma completa y no apoyándose en lo que yo tengo definido como atributos y métodos.
01:06:57
¿Cómo lo puedo bloquear en la clase persona?
01:07:03
Para que la clase alumno no herede la clase persona,
01:07:06
indicando la etiqueta final relacionada con una clase.
01:07:10
Fijaros cómo ahora ya este no me compila.
01:07:17
La supuesta clase alumno que heredaba la clase persona ahora ya no me compila. ¿Por qué? Porque en la clase supuesta clase persona, que es la clase 1P1, hemos puesto aquí la etiqueta final. Si quito aquí la etiqueta final de nuevo, si me vengo aquí, pues ya me deja.
01:07:19
en atributos lo convierte una variable en una constante
01:07:38
la etiqueta final relacionada con clases hace que
01:07:44
sea posible ya la herencia, no tenga clases hijas
01:07:49
y luego tenemos también
01:07:54
la posibilidad de poner la etiqueta final en métodos
01:07:57
que tiene nuevamente un significado diferente
01:08:01
esta es la clase hija de esta clase
01:08:04
¿verdad? de la supuesta clase persona
01:08:09
entonces vamos a poner aquí, vamos a crear aquí un método
01:08:13
public
01:08:15
void
01:08:16
saludar, vamos a llamarlo, mirad, este
01:08:22
método, saco un system.out.println
01:08:29
saludando desde la clase padre, fijaros
01:08:33
la clase 1p1
01:08:47
que sea clase persona, ya la podría haber llamado así desde el principio
01:08:51
cuando instanciemos objetos de esta clase
01:08:55
podríamos llamar al método saludar
01:08:58
y nos diría saludando
01:08:59
el de la clase padre
01:09:02
la clase herencia
01:09:03
tiene sus propios
01:09:05
métodos, tiene el main, podría tener
01:09:09
otros métodos más definidos por aquí
01:09:11
tiene sus propios
01:09:13
atributos y como
01:09:15
clase hija
01:09:17
de la clase persona
01:09:19
de la clase 1P1
01:09:21
tiene aquellos atributos definidos
01:09:23
en la clase padre, los que no sean privados, y aquellos métodos
01:09:25
definidos en la clase padre. Con lo cual, si yo pongo aquí
01:09:31
en el main, por ejemplo, para el objeto de la clase
01:09:35
P1, 1P1, voy a comentar esto
01:09:40
y hacemos código por aquí, nuevo, arriba.
01:09:49
Si yo cojo y digo, mira, quiero definir un objeto de la clase herencia.
01:09:57
Este objeto de la clase herencia es
01:10:11
tendrá, lógicamente acceso, tendrá sus atributos
01:10:14
entonces mioj.inunmat
01:10:18
está disponible, un atributo suyo, faltaría más
01:10:24
tengo la posibilidad de acceder a mis propios
01:10:32
métodos, vamos a poner aquí un public void
01:10:35
salu, vamos a llamarlo de momento, luego lo
01:10:39
renombraremos, ponemos aquí un system.out.println, saludo desde el hijo, pues podrá acceder a sus
01:10:45
métodos, podríamos llamar meof.salud, voy a ponerlo bien, voy a ponerlo en minúsculas que los métodos
01:11:05
tienen que empezar con minúsculas, hace a sus atributos y a sus métodos como es lógico, podemos
01:11:27
poner mi
01:11:36
oj.saludar
01:11:37
Este saludar, ¿por qué lo tiene disponible?
01:11:42
Si no lo he definido aquí, pues lo tiene disponible porque
01:11:44
clase herencia es hija de clase 1p1
01:11:47
y en clase 1p1 tenemos definido
01:11:52
el método saludar. Por herencia lo ha recibido.
01:11:56
Y luego, fijaros que aquí tenemos una serie de
01:11:59
atributos también y entero
01:12:02
que también están disponibles aquí por herencia.
01:12:04
y off punto y entero es decir tiene acceso a atributos de la propia clase métodos de la
01:12:08
propia clase atrib un método heredado de la clase padre un atributo heredado de la clase padre claro
01:12:22
si yo ejecutó esto vamos a ver qué resultado nos da estamos en la clase herencia aquí este
01:12:30
es el otro no me lo permitía porque no tenía un mail bueno me dice saludos de fijaros bueno
01:12:49
asigna este valor, miog saludo, dice saludo desde la clase hijo,
01:12:56
que es lo que hemos puesto aquí, y luego si pongo, llamo al método saludar,
01:13:04
como consecuencia de haber llamado este, dice saludando desde la clase padre,
01:13:09
que es este otro.
01:13:15
En las cuestiones de herencia, nosotros tenemos la posibilidad de ejecutar métodos
01:13:20
que sigan el comportamiento de lo definido en la clase padre,
01:13:26
como acabamos de ver ahora mismo, el método saludando.
01:13:30
Pero resulta que si esta es la clase persona y está resultando ser clase padre de una clase alumno
01:13:33
y de una clase profesor, podría ser que los profesores y los alumnos saludásemos de forma diferente.
01:13:45
Si tenemos definido el método saludar aquí en la clase padre,
01:13:51
diciendo saludando es de la clase padre, tanto si ejecutamos
01:13:57
el método saludar por parte de un alumno como por parte de un profesor
01:14:01
si está utilizando ese método, pues saludará de la misma
01:14:05
forma en todos los casos. Pero podría darse el caso
01:14:09
que quisiéramos que los alumnos y los profesores saludaran de forma
01:14:13
distinta. Entonces, a pesar de tenerlo disponible por herencia
01:14:17
es posible en esta clase sobre escribir ese método para que justo
01:14:21
se comporte de una forma diferente y sobre escribir el método lo que implica es hacer definir también este método en la clase hija.
01:14:25
Entonces yo cojo y digo aquí el método saludar, aquí podría poner saludando desde la clase alumno.
01:14:40
Ahora esta clase que estamos haciendo el supuesto de que es la clase alumno tendría sus propios atributos,
01:14:55
atributos, tendría por herencia un método saludar, que si lo llamamos, si no existe
01:15:02
en su propia clase, utilizaría este, pero como lo hemos sobrescrito aquí, el que va
01:15:08
a utilizar va a ser el propio. Entonces, si en la clase alumno y profesor resulta que
01:15:15
decimos que heredan de la clase persona, que sería esta, heredaría los atributos
01:15:21
de edad, de nombre, la posibilidad de utilizar su saludar, pero como queremos que saluden
01:15:27
de forma distinta uno y otro, lo sobreescribimos en ambas clases y en ambas clases tenemos
01:15:34
la posibilidad de poner un código diferente y así no utiliza el código que está disponible
01:15:39
en la clase padre.
01:15:43
Si yo cojo ahora aquí y ejecuto, ahora ya no pone saludando desde la clase padre, sino
01:15:45
que pone saludando desde la clase alumno.
01:15:53
entendiendo que está la clase alumno mira vamos a crear un momento la una clase profesora aquí
01:15:56
la clase profesor queremos también que herede de la supuesta clase persona que era la clase 1
01:16:03
es que le hacemos a la clase profesor le decimos también que herede desde esta lo tenemos si me
01:16:17
vengo al main fijaros que la clase herencia y profesor está en el mismo paquete pues ahora
01:16:31
aquí en el mail, yo podría coger y decir
01:16:36
profesor
01:16:38
prof1
01:16:39
Igual, crear un objeto de la clase
01:16:43
profesor. Fijaros, este objeto
01:16:45
de la clase profesor tendrás
01:16:50
Bueno, a ver
01:16:51
porque
01:17:02
estamos utilizando Eclipse y es muy listo
01:17:03
Eclipse, claro, los ides. O sea,
01:17:06
me lo ha metido, se ha dado cuenta
01:17:08
Eclipse de que me hacía falta.
01:17:10
Entonces ha cogido y lo ha puesto.
01:17:12
Pero, o sea, si tú lo estás
01:17:14
haciendo en un editor de texto que
01:17:16
no sea un IDE, claro, pues lo tienes que poner, sí, sí, claro, sí, sí, fijaros que la clase
01:17:17
profesor la he definido abierta, no he definido ningún método, ni ningún atributo, ni nada, pero
01:17:31
directamente tiene disponibles algunos por herencia desde la clase 1P1, que es la que estamos
01:17:37
suponiendo clase como clase persona. Entonces, si yo me vengo aquí
01:17:44
y digo que prof1.
01:17:48
Fijaros cómo tiene disponible saludar. ¿Cómo saludará
01:17:53
el profesor? Pues el profesor dirá, voy a
01:17:56
buscar un código que me dé respuesta al método saludar. ¿Lo tengo aquí?
01:18:00
No lo tengo aquí. Voy a utilizar el que tengo disponible como herencia
01:18:04
desde aquí. Con lo cual el profesor utilizará este saludar
01:18:09
y me saldrá un saludando de la clase padre.
01:18:13
En el caso de este otro objeto, que es la clase herencia,
01:18:16
la que estábamos haciendo el supuesto que fuese la clase alumno,
01:18:21
dirá, me piden que salude.
01:18:25
¿Veis? Por aquí.
01:18:27
Este saludar, ¿tengo yo implementado un saludar?
01:18:28
Sí.
01:18:31
Pues voy a utilizar el que tengo yo implementado.
01:18:31
En realidad, anteriormente, si no lo tuviera aquí implementado,
01:18:34
tendría uno por herencia de la clase persona.
01:18:36
Pero como lo tengo sobrescrito, en términos de la programación orientada a objetos, utilizo el propio. El profesor que también hereda de la clase persona, ¿lo tiene sobrescrito o no? Pues como no lo tiene sobrescrito, utiliza el que tiene disponible, que es el que está en la clase persona.
01:18:40
Entonces, si ahora ejecutamos de nuevo la clase herencia, fijaros cómo me dice, bueno, me dice primero un saludo desde la clase hijo, bueno, pues porque hacemos una llamada a un método propio, este ni estaba heredado ni nada, luego dice saludando desde la clase padre, desde la clase alumno, este saludar de un objeto perteneciente a la clase herencia, clase alumno de la que estábamos hablando, tiene disponible dos saludar, uno, heredado desde la clase padre, pero es que resulta que lo tiene que hacer.
01:18:58
aquí sobre escrito no tiene aquí sobre escrito me muestra el saludando el de la clase alumno y luego
01:19:31
otro objeto en este caso de la clase profesor llama al método saludar resulta que el profesor
01:19:39
no tiene sobre escrito el método saludar cuál va a utilizar el que sí que tiene disponible como
01:19:44
herencia es de la clase persona entonces este coge y me muestra el saludando el de la clase
01:19:50
padre bueno todo esto que ya os digo cuando hablemos de la herencia lo vamos a repasar de
01:19:56
nuevo pero explicar la etiqueta final relacionada con un método no tiene sentido si no entendéis
01:20:02
este contexto pues si aún hemos dicho si a un atributo le ponemos final se convierte en una
01:20:07
constante si a una clase le ponemos final no permite ya herencia de esa clase y si a un
01:20:14
método le ponemos final fijaros el método saludar lo que estás bloqueando es la posibilidad de
01:20:20
sobrescribir ese método en clases hijas es que ahora ya no me compila aquí
01:20:29
etiqueta final en una clase que resulta ser padre de otras lo que hace es
01:20:34
bloquear la posibilidad de sobre escribir ese método de las clases hijas
01:20:42
el método la etiqueta final en una clase evita que se puede utilizar esa clase
01:20:47
como padres en todo su conjunto en este caso lo único para el método evita que
01:20:53
se sobreescriba.
01:21:00
Ambar2 en el contexto de la herencia.
01:21:02
Matices distintos, pero en el contexto
01:21:04
de la herencia. Y etiqueta final en un
01:21:06
atributo convierte una variable
01:21:08
en
01:21:09
una constante.
01:21:10
¿Se entiende?
01:21:18
Vale.
01:21:27
Bueno, pues algunas
01:21:29
cosillas más de las que voy teniendo por aquí
01:21:31
apuntadas.
01:21:33
Bueno, hablo...
01:21:36
Tengo aquí apuntado que
01:21:40
en algún sitio o de algún sitio
01:21:41
deducido que podría ser interesante hablar del ámbito
01:21:43
de las variables.
01:21:46
Esto sí que lo hemos hablado más veces también.
01:21:49
En Java, digamos que el código se va definiendo por bloques
01:21:54
y estos bloques se van identificando con llaves.
01:21:58
Tenemos la clase, aquí definiendo una clase,
01:22:02
esta clase va de aquí hasta esta llave.
01:22:05
Todo lo que hay entre la llave de apertura y cierre
01:22:08
pertenece a esa clase.
01:22:10
un método, pues lo tenemos aquí, entonces todo lo que tenemos aquí
01:22:11
pues va entre, eso es el código que tiene que ver
01:22:15
con el método saludar, entonces las variables tienen
01:22:19
un acceso en unos determinados ámbitos
01:22:23
entonces el ámbito es en el que están definidos
01:22:26
entonces estas variables están definidas para poderse utilizar
01:22:31
en el ámbito de la clase en su conjunto
01:22:34
Si tú defines aquí una variable, está definida en el ámbito de este método. En este método, si ponemos inti entero puff, aquí en el ámbito del método saludar resulta que hemos definido una variable que se llama i entero puff.
01:22:38
Y resulta que este nombre coincide con este. Si yo, aquí defino la variable, si yo cojo aquí y asigno un valor a esa variable, ¿a cuál me estoy refiriendo? Pues al del ámbito más cercano, a esta variable y no a esta.
01:23:02
A efectos funcionales, digamos, o a efectos de recursos en el ordenador, cada una de las variables tendrá una zona de memoria RAM diferente que será donde se guardará su valor.
01:23:20
He estado muy pesado durante muchas semanas hablando de la RAM, pues cuando construimos, definimos una instancia de esta clase y creamos un objeto con new, se creará una variable para sus atributos, entonces se cogerá un espacio de memoria RAM para esta variable.
01:23:34
¿En qué momento se liberará esta memoria RAM? Pues habrá un momento en el que dejará de ser útil, que será el momento en el que salga del ámbito el objeto ese donde lo hayamos definido y luego una vez que ya no es útil para nuestro programa porque ya no está disponible el objeto para el que se había definido esa variable, pues el recolector de basura terminará liberando la memoria RAM.
01:23:53
A ver, el método finalice, si intentas localizarlo en código Java, pues si miras un millón de líneas de código lo vas a ver en un sitio o en ninguno.
01:24:23
Yo creo que no se llama nunca. En Java siempre se deriva a que eso suceda cuando el recolector de basura, que es un código que está por ahí detrás, del cual nosotros no nos preocupemos, se ejecute.
01:24:47
¿En qué casos podría ser muy interesante llamar al método finalice? Cuando se llama al método finalice es lo contrario al constructor. El constructor sí resulta muy útil porque cuando vamos a querer empezar a utilizar un objeto nos puede interesar que tenga ciertos valores subparámetros o para que pasen ciertas cosas.
01:25:05
imagínate que es un estadio
01:25:28
y está entrando gente
01:25:32
y dices, pues mira, me interesa
01:25:33
no tanto dar un valor a uno de sus atributos
01:25:36
de esta instancia del espectador
01:25:38
que acaba de pasar al estadio
01:25:42
sino que me interesa que cada vez
01:25:43
que acceda una nueva persona
01:25:44
se escriba en una base de datos
01:25:46
nueva persona accedido
01:25:49
en un fichero de un log
01:25:51
o sea, cuando queremos que al crear un nuevo objeto
01:25:52
suceda algo, inicializar sus atributos
01:25:55
o hacer ciertas acciones, utilizas el constructor.
01:25:57
Y el finalice podría entenderse como un método que fuese el destructor.
01:26:01
Cuando deja de existir un determinado objeto, pues que pasen ciertas cosas.
01:26:05
En tanto en cuanto inicializar variables, pues ya no tiene sentido,
01:26:12
porque justo ya está desapareciendo ese objeto,
01:26:16
¿para qué quieres tener variables inicializadas?
01:26:18
Si quieres que pase algo muy particular de un código que pongas,
01:26:21
pues bueno, podrías intentar llamar al método
01:26:25
finalice en ese caso, o
01:26:26
en el momento que lo vas a cerrar, llamar a un método
01:26:28
que haces tú, método finalice
01:26:30
no se suele programar nunca
01:26:33
pero existe y bueno, por eso aparece por ahí
01:26:34
digamos que lo podrías entender como
01:26:37
un destructor, igual que el otro es el
01:26:39
constructor, como un destructor del objeto
01:26:40
cuando llamabas
01:26:42
al método finalice
01:27:16
estaba terminando ya el programa, porque igual
01:27:17
termina el programa antes de que el recolector
01:27:20
de basura, estás como forzando que se llame
01:27:22
pero igual termina hasta antes el programa
01:27:24
ponme, ponme, de tal forma
01:27:25
yo te tengo que decir
01:27:27
que no estoy, o sea, para coger y hacer un ejercicio
01:27:30
aquí directamente, como es algo que no se usa prácticamente
01:27:32
nunca, no estoy muy familiarizado
01:27:34
con trabajar con él
01:27:36
de tal forma
01:27:37
no sé si tienes localizado
01:27:38
justo el ejercicio que es
01:27:42
o me lo pones en el foro
01:27:43
e intento echarle un ojo yo y lo ejecuto
01:27:45
a ver si doy con ello
01:27:47
vale, pues
01:27:48
bueno, en cualquier caso lo he hecho yo luego un ojillo
01:27:55
y os digo, a ver si lo hago
01:27:58
funcionar. Ya te digo que
01:28:02
luego en el mundo real no vas a ver el finalice
01:28:05
ese prácticamente nunca, con que
01:28:08
de cara aquí a este curso, con que entiendas
01:28:12
que se podría considerar como un destructor
01:28:16
pensando en esa idea
01:28:18
en un momento dado podría plantearse el finalice
01:28:22
como eso, está desapareciendo el objeto, pues es el momento
01:28:25
Podría ser el momento de restar uno al número de personas que están en el estadio o al número de objetos que se han creado. Nada, no se suele implementar nunca. De todas formas, lo he hecho yo durante estos días un ojillo y si llego a una conclusión clara de una buena forma de utilizarlo, os lo comento.
01:28:28
O bien en la próxima tutorial os escribo una entrada en el foro. Vale. Vale, pues lo miro, ¿vale? Y os pongo una entrada ahí en el foro. Vale, estábamos hablando de, ah, vale, de los ámbitos. Pues nada, esto es lo que os decía entonces de cuando tú creas un nuevo objeto, pues lógicamente necesitas para sus atributos un espacio de memoria RAM.
01:28:53
y esta variable la estamos definiendo en el ámbito de la clase
01:29:33
cuando quedará para liberarse
01:29:37
quedará ese espacio de memoria RAM para liberarse en el momento
01:29:41
en el que desaparezca el objeto, que básicamente por un objeto
01:29:45
su ámbito podríamos decir que es la clase completa
01:29:49
si de vez en cuando en ciertos sitios del código
01:29:52
se llama al método saludar, pues justo este método tiene este otro
01:29:57
ámbito. Entonces, si yo cojo y defino aquí unas variables, en el momento
01:30:01
en el que estoy definiendo estas variables, se reservará espacio de memoria
01:30:05
para estas variables también, igual que para los atributos antes
01:30:10
cuando definíamos un nuevo objeto. ¿Y cuándo dejan de ser útiles
01:30:13
estas variables? Pues si esta variable está definida en este ámbito, que es el
01:30:18
del método saludar, estará disponible esa variable entre la
01:30:21
apertura y el cierre de las llaves. Una vez llegado aquí, esa variable ya no tiene
01:30:26
uso ninguno, con lo cual el recolector de basura terminaría también
01:30:29
liberando ese espacio. Si definimos con un mismo nombre en diferentes
01:30:34
ámbitos que uno recoge al otro una variable con el mismo nombre, pues
01:30:40
se hace referencia a la variable que es más cercana. En este caso, fijaros
01:30:45
como Ecclesia al ponerme sobre esta variable me está poniendo un poquito
01:30:50
oscurecida la que está definiendo. Y si a pesar
01:30:55
de todo, dentro de este método, quiero hacer referencia a esta otra, pues como
01:31:00
hacemos habitualmente los constructores para pasar la información, podemos
01:31:03
utilizar la etiqueta dis, que quiere decir yo mismo,
01:31:07
mi propia clase, entonces yo pongo aquí el nombre de la variable
01:31:11
precedido por dis
01:31:15
y entonces ahora si me pongo sobre esta, fijaros como Eclipse
01:31:21
hacer que compile, si me pongo sobre esta variable
01:31:24
fijaros como Eclipse ahora la que me pone en negrita es esta y hace
01:31:32
considera que es esta y no la del ámbito más cercano porque le he puesto el dis
01:31:35
y esta otra, pues como no le he puesto el dis, pues considera
01:31:39
que es esta, no me lo pone ahí en negrita
01:31:43
pero bueno, esta se refiere a esta la más cercana, no, es que se llaman diferentes
01:31:53
las variables, hacerla coincidir, bien, ahora ya
01:32:00
se llaman igual, entonces si me pongo en esta se refiere a esta y si me pongo sobre esta se refiere a la
01:32:05
local. Bueno, eso respecto a los ámbitos. Fijaros que un ámbito
01:32:09
al final es algo que está encerrado entre unas llaves.
01:32:15
Para la clase es esto, desde aquí hasta el final, para el método saludar es este.
01:32:20
Aunque es una cosa que tampoco se utiliza mucho, existe la posibilidad de
01:32:24
definir ámbitos que no estén relacionados con nada y se definen
01:32:27
con unas llaves. A ver, creo recordar, a ver, si yo hago esto
01:32:31
Fijaros, dentro de un método, como he abierto aquí unas llaves, vamos a tabularlo para verlo más claro con estas llaves, si yo ahora intento acceder a esta variable y le pongo un valor de 9, me compila, pero fijaros a qué variable se refiere, se refiere a la de clase.
01:32:35
no se refiere a esta, ¿por qué? porque esta variable
01:32:56
a pesar de que estas llaves no están asociadas a un método ni a una clase
01:33:00
están definiendo un ámbito, no sé si lo veis, que me pongo aquí y no se refiere
01:33:04
a esta variable, aunque a pesar de que comparten
01:33:11
código en el mismo método, sino que se refiere a la variable de clase
01:33:14
¿por qué? porque ya os digo, esta está definida en el ámbito
01:33:19
de estas llaves, es decir, existe esta posibilidad
01:33:23
Pero bueno, no se suelen poner así llaves, a no ser que sea para identificar bloques SIF o para bucles o métodos o bien identificar clases en su conjunto.
01:33:26
Bueno, esto os puedo contar más o menos de los ámbitos.
01:33:46
Otra cosa de la que habíamos estado hablando otro día es de los constructores copia.
01:33:51
No sé si os acordáis de ellos. Los constructores copia son los que definimos en una clase. Haciendo un mini repaso de los constructores, los constructores son métodos que se llaman igual que la clase, suelen ser públicos, son los únicos métodos que no devuelven nada, no tienen una instrucción return, pero no lo indicamos aquí en los constructores.
01:33:57
Y pueden estar sobrecargados, os acordáis de la sobrecarga de métodos que también hemos hablado en algún momento de ella y volveremos a repasarlo.
01:34:36
Si yo cogiese y definiese dos métodos, los constructores como cualquier otro método de la clase también lo aceptan, dos métodos así,
01:34:46
que no nos permitiría, si hacemos una llamada
01:34:56
a este constructor, a un constructor sin parámetros, no nos permitiría identificar
01:35:01
si nos estamos refiriendo al código que está implementado
01:35:05
aquí, en este método o en este otro. Entonces, como hay una
01:35:09
discrepancia, no es posible identificar a cuál nos referimos
01:35:13
si hacemos, por ejemplo, este profesor
01:35:16
aquí estamos llamando al constructor, fijaros, llamada a un método
01:35:23
constructor sin pasarle parámetro ninguno, pues se vendría aquí al código y diría
01:35:27
¿cuál quieres que ejecute? ¿este o este? Si aquí me has puesto un código que puede ser
01:35:31
diferente del que me has puesto aquí. Entonces, esto no lo acepta.
01:35:35
Es igual que si tenemos una variable con...
01:35:39
Intentamos poner a dos variables el mismo nombre. Entonces, lo que sí que nos acepta es
01:35:42
si ponemos... Hacemos que tengan
01:35:47
alguna diferencia. Entonces, aquí este no recibe ningún
01:35:53
parámetro y este recibe uno aquí si nos venimos en este constructor está claro que no le estamos
01:35:57
pasando parámetro alguno no hay lugar a dudas entre estos dos cual tendría que ejecutar el
01:36:04
que no recibe ningún parámetro y si le ponemos que como parámetro reciba una cadena de caracteres
01:36:08
pues esto me seguiría con compilando por aquí ve como veis y cuando se viniese aquí a buscar
01:36:15
el constructor, diría, ¿cuál de ellos tengo que ejecutar? ¿Este o este?
01:36:28
Pues oye, si me has pasado como parámetro una cadena de caracteres,
01:36:31
este no recibe ninguna, pues querrás que se ejecute este código.
01:36:36
Entonces esto me compila porque no hay discrepancia, no hay lugar a dudas
01:36:39
cuál de los dos tiene que ejecutar. Esto, el hecho de tener diferentes métodos,
01:36:44
en este caso el método constructor, con el mismo nombre que los diferencia
01:36:50
el número de parámetros, el tipo, el número de parámetros que tienen disponibles
01:36:55
y nos garantiza que no hay lugar a dudas cuál de los dos se tiene que ejecutar cuando lo llamemos
01:36:59
es lo que se llama sobrecarga de métodos, ¿vale?
01:37:03
No sobre escritura, que era lo que hablábamos antes de la herencia, sobrecarga.
01:37:08
Entonces, el constructor copia, que es otra de las cosas que tengo por aquí apuntadas,
01:37:13
es un constructor, con lo cual
01:37:20
será public, se llamará
01:37:22
como la clase, profesor
01:37:25
su utilidad típicamente será
01:37:26
el momento en el que estamos haciendo un
01:37:29
nuevo objeto
01:37:30
por aquí, verdad, no sé si alguien
01:37:31
ha levantado por ahí la mano, cuando me queráis
01:37:38
decir algo, decídmelo a la bravas
01:37:40
no levantéis la mano porque
01:37:42
porque no estoy muy pendiente
01:37:44
de si me las andáis levantando
01:37:46
igual alguien la está levantando hace rato
01:37:48
y está esperando a que le dé paso
01:37:49
y no me estoy ni enterando
01:37:51
Si queréis decirme algo, me avisáis. Entonces, el constructor copia puede ser un constructor que sobrecarga a otros y que el parámetro que recibe es una referencia a un objeto de la misma clase.
01:37:53
¿Y para qué utilizamos esto? Pues mirad, si queremos tener varios objetos que sean exactamente igual, que cada uno estará situado en una zona diferente de memoria,
01:38:14
porque son objetos distintos, pero puede ser que todos sus atributos
01:38:25
queramos que tengan el mismo valor, pues podemos utilizar el constructor.
01:38:29
Lo normal será utilizar el constructor copia.
01:38:34
Mirad, si aquí cogemos y definimos, ponemos string ese nombre
01:38:38
para el profesor, int y edad, estos dos atributos,
01:38:43
aquí podemos crear un primer profesor con este constructor, por ejemplo,
01:38:50
que no recibe ningún atributo, y a este profesor podemos coger y decirle
01:38:56
prof1, punto, y aplicarle valores a sus atributos.
01:39:07
Es decir, que su nombre sea Valeria y que su edad sea 13 años, por ejemplo.
01:39:12
Entonces, prof1 resulta que tiene, es un objeto de la clase profesor
01:39:30
al cual hemos asignado un nombre de Valeria y una edad de 13 años.
01:39:34
Y ahora resulta que podríamos querer tener una segunda persona, un segundo profesor, un profesor con 13 años, igual lo estamos sobreexplotando, pero bueno, ahora que me di cuenta, podríamos tener un segundo profesor que queremos que de partida tenga los mismos datos que el profesor 1.
01:39:38
Bueno, pues así nos está exigiendo el programa. Podríamos coger y hacer esto, construir un segundo profesor y asignarle sus valores, en este caso sería prof2, o lo que podemos hacer es utilizar el constructor copia, que sería hacer esto y llamar al new del profesor utilizando el constructor y pasándole una persona.
01:39:57
en este caso el prof.1
01:40:21
y aquí que es lo que vamos a hacer
01:40:23
lo que vamos a hacer va a ser
01:40:25
en el constructor copia
01:40:27
decir que
01:40:29
dis de este el ese nombre
01:40:31
es decir
01:40:33
la variable
01:40:35
de el objeto que está
01:40:36
llamando al constructor, fijaros
01:40:39
el que está llamando al constructor es el
01:40:41
profesor2
01:40:43
su nombre queremos que sea
01:40:44
igual a un
01:40:47
prof. ese nombre. Aquí, en este profesor
01:40:49
que ha recibido como parámetro, resulta que le estamos aplicando
01:40:54
estamos pasando el profesor 1. Entonces, ¿qué estamos haciendo?
01:40:57
Esta posición de memoria para el profesor 1, habíamos asignado a su nombre
01:41:02
Valeria, y esta posición de memoria se está copiando como parámetro
01:41:06
en esta posición de memoria, con lo cual esto está apuntando en memoria RAM
01:41:10
al mismo sitio donde está apuntando prof1. Y resulta que prof1, su variable ese nombre
01:41:14
es Valeria, entonces
01:41:18
un prof. ese nombre que tendrá
01:41:20
Valeria, y aquí se lo estamos asignando
01:41:22
al objeto
01:41:24
con el dis, al atributo del
01:41:26
objeto
01:41:28
de quien está ejecutando en este momento el constructor
01:41:28
que es
01:41:32
este otro, el profesor
01:41:33
2, entonces estamos copiando los atributos
01:41:36
de un profesor
01:41:38
que estamos pasando al constructor
01:41:40
como parámetro
01:41:42
a los atributos
01:41:44
de este otro. Este es el constructor copia. Entonces haríamos esto
01:41:46
de igual forma para la edad. Y ahí tenemos el constructor copia.
01:41:50
En realidad, aquí como no tenemos como un parámetro
01:42:00
ni ese nombre ni edad, si
01:42:04
quitamos el dis, se mantendría
01:42:07
que las variables a las que hace referencia este constructor
01:42:11
siguen siendo las de la clase. Dice que es el nombre
01:42:15
Si utilizamos el dis, también sigue diciendo que son estos atributos.
01:42:20
¿Alguna dudilla por ahí tenéis? ¿Alguna cosilla queréis preguntarme?
01:42:32
Hemos hablado de unas cuantas cosas hoy, la verdad.
01:42:37
Unas cuantas etiquetas. No sé si os han quedado más o menos claras.
01:42:41
Todavía tengo unas cuantas cosas más apuntadas por aquí.
01:42:49
Yo creo que para el lunes que viene. Me parece que lo vamos a ir dejando ya por aquí.
01:42:53
Si no tenéis alguna duda, hasta donde hemos visto.
01:42:57
Nada nuevo, miro lo del finalice, de todas formas, a ver si, ya digo que no, que con este método no he trabajado mucho, pero lo miro para ver si lo concretamos, y yo bien en la siguiente tutoría os cuento, os pongo una entrada en el foro, y si no tenéis nada, pues aquí paramos, el lunes que viene ya continuamos con el resto de cosas de este tema.
01:43:05
Y si tenéis dudas durante la semana, ya sabéis, me ponéis entradas en el foro. Estoy bastante pendiente de él.
01:43:29
Pues venga, pues nada, a vosotros. Que tengáis buena semana. Hasta luego.
01:43:39
- Materias:
- Programación
- Niveles educativos:
- ▼ Mostrar / ocultar niveles
- Formación Profesional
- Ciclo formativo de grado superior
- Primer Curso
- Segundo Curso
- Autor/es:
- JM
- Subido por:
- Jose Manuel M.
- Licencia:
- Dominio público
- Visualizaciones:
- 43
- Fecha:
- 13 de enero de 2025 - 19:20
- Visibilidad:
- Clave
- Centro:
- IES ALONSO DE AVELLANEDA
- Duración:
- 1h′ 43′ 46″
- Relación de aspecto:
- 1.78:1
- Resolución:
- 1920x1080 píxeles
- Tamaño:
- 199.29 MBytes