unidad 1 introducción a la programación orientada a objetos.ilapep.mx/poo/poo1_con_cpp.pdf ·...

15
Unidad 1 Introducción a la Programación orientada a objetos. J. Fco. Jafet Pérez López, UNEDL Objetivo: Comprender los conceptos básicos de la programación orientada a objetos. El ser humano puede ser considerado como un sistema procesador de información. Este sistema recibe los datos que va a procesar a través de sensaciones. Se genera una sensación cuando uno de nuestros sentidos es estimulado por el entorno que le rodea, el órgano del sentido (vista, tacto, oído, gusto, olfato) recibe la información, la transmite por los nervios (como mensajes nerviosos) al cerebro que recibe la información y la procesa. Una vez que nuestros sentidos captan los objetos del entorno y envían la sensación al cerebro, éste le da un significado. Este proceso mental lo llamamos percepción. Podríamos decir que la percepción es el proceso por el cual obtenemos datos del exterior y los organizamos de modo significativo en nuestro interior para tomar conciencia del mundo que nos rodea. A pesar de que nuestros sentidos son estimulados constantemente no siempre respondemos a los estímulos provenientes de nuestro ambiente ya que contamos con mecanismos que impiden una sobrecarga de información en nuestro cerebro. Los sistemas sensoriales permiten que el organismo obtenga la información necesaria para funcionar y sobrevivir. La percepción es un proceso de selección. El mecanismo que permite al cerebro seleccionar las sensaciones que le llegan se le denomina atención. La atención actúa como filtro de la información recibida y es un mecanismo de alerta ante los datos que son importantes. La atención es subjetiva; percibimos lo que nos interesa (predisposición perceptiva). La atención se ve afectada por factores externos como la intensidad, el tamaño, el color, etc., del objeto captado e internos como una necesidad biológica o los intereses sociales del individuo o bien, qué tan agradable o desagradable resulte la sensación percibida. Además de lo anterior, al interpretar los datos, lo que esperamos puede influir en lo que vamos a percibir (se juzga antes de conocer). También los recuerdos, afectos y experiencias influyen en la percepción. De igual manera, el contexto social, la educación y la cultura influyen en la percepción. Hay variaciones perceptivas entre individuos de unas culturas y otras porque aprendemos de los demás a percibir el mundo.

Upload: others

Post on 18-Jan-2020

1 views

Category:

Documents


0 download

TRANSCRIPT

Unidad 1

Introducción a la Programación orientada a objetos.

J. Fco. Jafet Pérez López,

UNEDL

Objetivo: Comprender los conceptos básicos de la programación

orientada a objetos.

El ser humano puede ser considerado como un sistema

procesador de información. Este sistema recibe los datos que va a

procesar a través de sensaciones. Se genera una sensación cuando uno

de nuestros sentidos es estimulado por el entorno que le rodea, el

órgano del sentido (vista, tacto, oído, gusto, olfato) recibe la

información, la transmite por los nervios (como mensajes nerviosos) al

cerebro que recibe la información y la procesa. Una vez que nuestros

sentidos captan los objetos del entorno y envían la sensación al cerebro,

éste le da un significado. Este proceso mental lo llamamos percepción.

Podríamos decir que la percepción es el proceso por el cual obtenemos

datos del exterior y los organizamos de modo significativo en nuestro

interior para tomar conciencia del mundo que nos rodea.

A pesar de que nuestros sentidos son estimulados constantemente

no siempre respondemos a los estímulos provenientes de nuestro

ambiente ya que contamos con mecanismos que impiden una

sobrecarga de información en nuestro cerebro. Los sistemas sensoriales

permiten que el organismo obtenga la información necesaria para

funcionar y sobrevivir. La percepción es un proceso de selección. El

mecanismo que permite al cerebro seleccionar las sensaciones que le

llegan se le denomina atención. La atención actúa como filtro de la

información recibida y es un mecanismo de alerta ante los datos que

son importantes.

La atención es subjetiva; percibimos lo que nos interesa

(predisposición perceptiva). La atención se ve afectada por factores

externos como la intensidad, el tamaño, el color, etc., del objeto

captado e internos como una necesidad biológica o los intereses

sociales del individuo o bien, qué tan agradable o desagradable resulte

la sensación percibida. Además de lo anterior, al interpretar los datos, lo

que esperamos puede influir en lo que vamos a percibir (se juzga antes

de conocer). También los recuerdos, afectos y experiencias influyen en

la percepción. De igual manera, el contexto social, la educación y la

cultura influyen en la percepción. Hay variaciones perceptivas entre

individuos de unas culturas y otras porque aprendemos de los demás a

percibir el mundo.

La percepción es el primer momento del proceso de

conocimiento, es el momento en que una serie de datos empíricos le

son dados a los sentidos y éstos lo captan. La abstracción es un proceso

posterior en la cual, de todas las cualidades que tiene el objeto

captado, el cerebro selecciona ciertas cualidades que ese objeto

comparte con otros afines y las une en lo que llamamos concepto.

Abstraer significa quitar, el cerebro quita cualidades y características

hasta darle un carácter único al objeto que se tiene en frente.

Por ejemplo si captamos una esfera pequeña de color verde,

aroma y sabor ácidos. Eso sería la percepción. El cerebro considera y

descarta algunos detalles (tiempo, espacio, accidentes en la forma,

color, tamaño, etc.), dejando sólo aquellas cualidades que la hacen

coincidir con algo que de lo que ya tiene un concepto (el color, aroma

y sabor mencionados arriba, por ejemplo). Eso sería la abstracción. Es en

ese momento en que podemos decir: "Esto es un limón". En caso de que

sea un objeto desconocido para el individuo, el cerebro se encargará,

por medio del proceso de abstracción de volver esa cosa un concepto,

aunque dicho concepto no siempre tenga un nombre definido.

En otras palabras el cerebro intenta, primero, extraer la forma del

objeto, cuando las sensaciones que se reciben son analizadas por el

sujeto en elementos y globalmente intenta clasificar esos elementos así

como el objeto en completo cuando ya está clasificado lo compara

con patrones que hay en la memoria, cuando concuerda ese objeto

con lo que hay en nuestra memoria acaba la percepción del objeto.

Cuando en la anterior etapa no se ha podido clasificar el objeto o se

presenta una ambigüedad entonces se utiliza la comparación con un

contexto, que es una interpretación o reconstrucción consciente del

objeto.

Cuando programamos, intentamos implementar un modelo de

solución de un problema del mundo real en una computadora,

aprovechando características como su velocidad para resolver

operaciones y su capacidad para almacenar y procesar información,

utilizándola como una herramienta para llevar a cabo nuestro trabajo

más fácil y rápidamente. La programación orientada a objetos nos

ayuda a que esa implementación sea lo más cercana posible a la

manera como solucionaríamos el problema en el mundo real

proporcionándonos mecanismos muy similares a los que utiliza nuestro

cerebro para percibir todo lo que le rodea.

Sin embargo, nuestro cerebro procesa el mundo real de manera

analógica y las computadoras son digitales, lo que significa que si

queremos llevar una solución a un problema desde el mundo real a una

computadora es necesario que lo especifiquemos de manera que la

máquina pueda entenderlo y procesarlo y eso implica que nuestra

especificación contenga la solución en términos finitos para ello

recurrimos a mecanismos como la abstracción, que es el proceso que

consiste en ignorar detalles para concentrarse en las características

esenciales de algo.

Todo lenguaje de programación ofrece un proceso de

abstracción sobre un concepto extraído del mundo real, en otras

palabras, un lenguaje permite un mapeo entre un problema espacial

(real) hacia uno maquinal que será aquel ejecutado por una

computadora. Es en esta capacidad de abstracción en la que reside la

facilidad/complejidad de generar programas funcionales capaces de

resolver el problema espacial.

La utilidad de la programación orientada a objetos radica en la

posibilidad de ésta técnica de reflejar la abstracción que el cerebro

humano realiza automáticamente durante el proceso de aprendizaje,

o, más generalmente, durante el análisis de información. Las personas

percibimos la realidad como un conjunto de objetos interrelacionados.

Dichas interrelaciones, pueden verse como un conjunto de

abstracciones y generalizaciones que se han ido asimilando desde la

niñez. Así, la programación orientada a objetos se adecua al

funcionamiento del cerebro humano, al permitir descomponer un

problema de cierta magnitud en un conjunto de problemas menores

subordinados del primero. Por tanto, la capacidad de descomponer un

problema o concepto en un conjunto de objetos relacionados entre sí, y

cuyo comportamiento es fácilmente identificable, puede ser muy útil

para el desarrollo de programas informáticos.

C++ es el lenguaje mediante el cual especificaremos la solución

de un problema en la forma como queremos que la computadora lo

resuelva. Es un lenguaje orientado a objetos, lo que significa que la

solución propuesta debe estar en términos de este modelo de

programación en el que un programa está definido como un conjunto

de objetos, enviándose mensajes entre sí con el objetivo de solucionar

un problema.

El lenguaje de programación C++ proporciona elementos de

construcción que nos permiten describir cómo son y cómo interactúan

entre sí los objetos que participan en un problema para solucionarlo.

Pero ¿qué es un objeto?

Todo es un objeto: Considere un objeto una variable especial, no

solamente guarda datos, sino también se pueden hacer solicitudes a

este Objeto en sí. En teoría, cualquier elemento en el problema espacial

(real) (edificios, servicios, automóviles, roles, u otra entidad) puede ser

representado como un objeto en un programa. Por lo que podríamos

decir que un objeto es una entidad con un límite bien definido e

identidad que encapsula un estado y un comportamiento. El estado se

representa por los atributos y las relaciones, mientras que el

comportamiento es representado por sus operaciones, métodos. Un

objeto es una instancia de una clase; es decir, es una entidad individual

que satisface la descripción de una clase o tipo.

Cada objeto se diferencia del otro por los valores de sus atributos.

Este conjunto de valores forman el estado del objeto, único para cada

instancia (estoy usando los términos instancia y objeto indistintamente

para referirme a lo mismo).

Un atributo es una propiedad que comparten los objetos de una

clase. En esencia, el proceso de abstracción que se requiere para

definir qué propiedades de un objeto son importantes en la solución de

tal o cual problema, es el mismo que realiza nuestro cerebro para ver lo

que le “conviene” o le interesa en los objetos del mundo real. Por lo que

los atributos estarán definidos en función del problema que se desea

resolver tomando en cuenta que las propiedades o características de

un objeto en el mundo real pueden ser tantas que sería muy difícil

representarlas en un modelo computacional.

Por ejemplo, si queremos desarrollar un programa relacionado

con la moda y queremos representar en él a personas del mundo real,

tal vez las propiedades que nos interesen de esas personas sean, el tipo

y color de piel, ojos y pelo, su estatura y medidas, etc., pero si el

programa que pretendemos construir se relaciona con el sistema de

nominas de una empresa, las personas tendrían propiedades o atributos

relacionados con su sueldo, las faltas que acumularon, el departamento

al que pertenecen, su antigüedad en la empresa, etc., y los detalles de

la piel, ojos, pelo, peso y medidas serían irrelevantes.

En el mundo real, los seres humanos no concebimos una

estructura (una cosa u objeto) sin pensar al mismo tiempo en el

comportamiento que presenta o puede presentar esa estructura (esa

cosa u objeto).

Los objetos también tienen un comportamiento definido por las

operaciones que puede realizar. Una operación es la especificación de

un servicio que puede ser requerido al objeto para que muestre un

comportamiento. En otras palabras, una operación es una abstracción

de algo que se puede hacer a un objeto que es compartido por todas

las instancias de la clase a la que pertenece el objeto. Lo anterior

significa que todo objeto de un mismo tipo puede recibir los mismos

mensajes y responderá de manera similar a ellos según lo especificado

en los métodos de las operaciones que son llamadas en dichos

mensajes.

Para realizar una solicitud de comportamiento a un objeto es

necesario enviarle un mensaje. Concretamente se puede pensar que un

mensaje es una solicitud para llamar una función u operación que

pertenece a cierto objeto.

Todo objeto tiene un tipo o clase a la que pertenece. Una clase es

una descripción de un conjunto de objetos que comparten los mismos

atributos, operaciones, relaciones y semántica. Una clase puede ser

vista como una plantilla o molde, un prototipo funcional, a partir del

cual se pueden crear o instanciar un conjunto de elementos con las

mismas características y comportamientos llamados objetos.

Es el orden natural de las cosas: las clases, provienen

precisamente del mundo real y constituyen lo que se llama el modelo

de dominio.

C++ provee un bloque de construcción que permite especificar

una clase para describir a los objetos que pertenecen a ella. Una vez

definida la clase, entonces, y solo entonces, será posible declarar

objetos de esa clase. Esta descripción debe adaptarse a la manera

como una computadora almacena y procesa la información, es decir,

debe ser una descripción finita y no permite ambigüedades.

En este documento, utilizare un ejemplo aplicable a todos los

conceptos que estudiaremos; este ejemplo es la representación de un

reloj del mundo real en un programa.

Para utilizar objetos de tipo reloj en mi programa, primero necesito

modelar la clase Reloj, a la que estos pertenecen.

Suponiendo que mi interés es utilizar relojes que solo me indiquen

la hora y puedan avanzar desde un tiempo inicial, un primer modelo de

la clase Reloj podría ser el siguiente:

Reloj

hora

min

seg

inicializar()

obtTiempo()

avanzar1Seg()

operaciones

atributos

Note como he buscado atributos y operaciones que para mi

parecen importantes, por ejemplo, no considere la marca o el color del

reloj porque para mí, estos atributos no son necesarios.

Para este ejemplo he diseñado una clase con tres atributos: hora,

min y seg, estos atributos tendrán un valor asignado en cada reloj que

yo utilice en mi programa y este valor podrá ir cambiando durante la

ejecución del mismo.

También he asignado tres operaciones a la clase, inicializar(),

obtTiempo() y avanzar1Seg().

inicializar() recibe tres parámetros enteros que utilizaremos para

enviar la hora, el minuto y el segundo iniciales de cada reloj que

utilicemos en el programa. obtTiempo() es una operación que nos

devolverá el tiempo del reloj en el momento que lo consultemos, la

operación debe regresar una cadena con el tiempo, por eso tiene un

tipo de retorno (string). Por último, la operación avanzar1Seg() nos

permitirá implementar el mecanismo del reloj para avanzar 1 segundo.

En el caso de las operaciones, debemos tomar en cuenta que

incluiremos aquellas que actuarán sobre los atributos o que los

manipularán de alguna manera, para este ejemplo, no nos serviría una

operación denominada asignarColor() si no hay un atributo que tenga

que ver con el color del reloj.

También hay ciertas reglas que tomaremos en cuenta en relación

a los nombres de las clases y sus propiedades:

Los nombres de las clases son expresiones nominales extraídas del

dominio del problema, iniciarán con mayúscula y si está formado por

dos o más palabras, cada palabra que lo forma comenzará también

con mayúscula. No llevará espacios en blanco ni guiones bajo.

Los nombres de los atributos, son expresiones nominales extraídas

del dominio del problema, inician con minúscula y si están formados por

dos o más palabras, cada palabra que lo forma inicia con mayúscula

excepto la primera.

Los nombres de las operaciones son expresiones verbales

(denotan una acción a realizar) extraídas del dominio del problema,

inician con minúscula y si están formados por dos o más palabras, cada

palabra que lo forma inicia con mayúscula excepto la primera.

Los atributos y las operaciones deben especificarse sin

ambigüedades y con el mayor detalle posible.

Los atributos son la estructura de los objetos y contienen

información propia de cada uno de ellos, esta información debe ser de

un tipo o pertenecer a alguna clase también. Así por ejemplo, los

atributos hora, min y seg de la clase Reloj contendrán valores numéricos

enteros en cada reloj por lo que los tres podría ser de tipo int o entero.

Los métodos de las operaciones (la implementación de las

mismas) trabajarán con datos que van a procesar, estos datos pueden

ser los mismos atributos o pueden recibirse como parámetros

(argumentos) antes de iniciar su procesamiento. De igual forma, las

operaciones regresarán referencias o información a quien solicite el

servicio de la operación, es decir devolverán “algo” y ese algo también

debe tener un tipo o pertenecer a una clase.

Todo esto puede especificarse en la definición de la clase:

En nuestro diseño inicial hemos agregado un tipo o clase para

cada atributo y hemos asignado un tipo o clase de retorno para cada

operación; también se ha indicado que la operación inicializar() recibirá

los parámetros h, m y s de tipo int para trabajar.

Podría ahora especificar la clase Reloj en C++, cuya primera

versión podría ser la siguiente:

class Reloj{ int hora; int min; int seg; void inicializar(int h, int m, int s); string obtTiempo(); void avanzar1Seg(); };

Reloj

hora : int

min : int

seg :int

inicializar(h, m, s : int) : void

obtTiempo() : string

avanzar1Seg() : void

Observe en el código anterior que una operación únicamente es

la especificación de un comportamiento que los objetos de la clase

podrán realizar (el qué). En este ejemplo aún no hemos indicado la

forma en la que lo llevarán a cabo (el cómo). En una implementación

completa de nuestra clase se deberá considerar el método que

implementará cada una de las operaciones; es decir, escribiremos

también el código necesario para llevar a cabo la función para que se

haya creado la operación.

Para este ejemplo, la operación inicializar, únicamente se

encargará de darle valores iniciales al estado del objeto, en el mundo

real sería como poner la hora exacta por primera vez al reloj.

Cada objeto Reloj creado posteriormente tendrá su propio

conjunto de atributos y cada uno tendrá valores distintos para ellos. Sin

embargo, la clase especificará de manera general como usarán esos

atributos las operaciones. Por ejemplo, el código del método para

inicializar un reloj cualquiera podría ser:

void Reloj::inicializar(int h, int m, int s){ hora=h; min = m; seg = s; }

Observe que la implementación del método quedará fuera de la

clase y que es posible que existan varias clases en nuestro programa

que tengan una operación llamada “inicializar”, para evitar alguna

ambigüedad se utiliza el operador de alcance (::) y el nombre de la

clase a la que pertenece el método que se está escribiendo.

Aquí se especifica que para poner la hora inicial de un objeto

Reloj, es necesario que el objeto conozca los valores iniciales (h, m y s)

que se van a asignar a los atributos hora, min y seg respectivamente. Por

ejemplo, si en un programa se tiene un objeto de la clase Reloj llamado

rolex y se desea que ese objeto se inicialice, se llamará a la operación

inicializar() indicando los parámetros necesarios para tal efecto:

rolex.inicializar(10, 25, 19);

La operación obtTiempo() regresará la hora completa de un reloj

en particular en algún formato. El código podría ser:

string Reloj::obtTiempo(){ char tiempo [16]; sprintf (tiempo, "%d:%d:%d", hora, min, seg); return tiempo; }

Regresaría el estado del

objeto en una cadena

con la forma hh:mm:ss

Y la operación avanzar1Seg() deberá implementar un mecanismo

para hacer que cualquier reloj de la clase avance un segundo de forma

similar a como lo haría un reloj en el mundo real. Aquí es necesario

especificar un algoritmo que lleve a cabo esta tarea:

Ese mecanismo puede ser representado en C++ dentro del método

avanzar1Seg() de la siguiente forma:

void Reloj::avanzar1Seg(){ if (seg < 59){ seg++; } else{ seg=0; if (min < 59){ min++; } else{ if(hora < 23){ hora++; } else{ hora=0; } } } }

inicio seg < 59 seg = seg + 1

no

seg = 0

min < 59 min = min + 1

min = 0

hora< 23 hora = hora + 1

hora = 0 fin

si

si

si

no

no

Como puede observarse, las operaciones de la clase se

implementan con los métodos que son líneas de código que definen

cómo ha de realizarse la operación.

Normalmente los atributos o propiedades de una clase están

ocultos al mundo exterior, es decir, al resto de clases o de entidades

que forman un sistema. Solamente se puede acceder a los valores de

tales propiedades a través de métodos de la clase dispuestos para tal

fin. Algunos de estos métodos son especializados y únicamente son

capaces de asignar o leer el valor de una propiedad, otros lo hacen

mediante operaciones o transacciones más o menos complejas.

Lo anterior para evitar que algún usuario de la clase pueda hacer

uso inapropiado de esta comprometiendo la integridad del estado de

algún objeto. Por ejemplo, considere la siguiente sentencia:

rolex.hora = 365;

Esta asignación no es lógicamente correcta ya que la hora de un

reloj no puede ser 365. Para evitar situaciones como la anterior se aplica

un principio denominado ocultamiento de la información. Este principio

sugiere que un objeto cualquiera provea una interfaz para comunicarse

con él, ocultando así los detalles de implementación de dicho objeto y

evitando el acceso directo a los datos del mismo.

Esto implica que en la clase se especifiquen operaciones para

validar cualquier manipulación del estado del objeto y para acceder a

los valores de sus atributos. Estas operaciones reciben el nombre de

operaciones de interfaz.

De manera general definiremos dos operaciones de interfaz para

cada atributo declarado en una clase:

La operación “poner” se encargará de asignar un valor al

atributo, deberá recibir dicho valor mediante un parámetro del mismo

tipo que el atributo. En su acepción más simple el método de la

operación poner consistirá únicamente en darle un valor al atributo en

cuestión, sin embargo, antes de ello es conveniente que el

programador valide el valor que está recibiendo la operación y se

asegure que no afectará la integridad del estado del objeto.

La operación “obt” obtendrá el valor del atributo y lo devolverá a

quien lo haya solicitado.

El siguiente código muestra una manera de implementar dichas

operaciones para el atributo hora de la clase Reloj:

void Reloj::ponerHora(int hora){ Reloj::hora=hora; } int Reloj::obtHora(){ return (hora); }

Nótese que la operación poner recibe un parámetro con el mismo

nombre que el atributo que va a afectar, para evitar una ambigüedad

en la asignación, hemos hecho uso del operador de alcance “::” por lo

que la asignación Reloj::hora = hora; se podría leer como: al atributo

hora del objeto actual ponle el valor del parámetro hora que está

recibiendo. De igual forma se pudo evitar la ambigüedad cambiando el

nombre al parámetro enviado:

void Reloj::ponerHora(int nvaHora){ Reloj::hora=nvaHora; }

Esta operación como está escrita, no resuelve el problema de la

amenaza a la integridad del objeto ya que una llamada a la misma

podría ser:

rolex.ponerHora(365);

Lo cual sigue siendo incorrecto, sin embargo, quise mostrar un

esquema generalizado de las operaciones poner y obtener, está claro

que el programador debe realizar las validaciones por código que crea

pertinentes para cada operación de interfaz. Por ejemplo, para evitar

una asignación como la anterior podríamos escribir algo como lo

siguiente:

void Reloj::ponerHora(int hora){ if (hora <= 23){ Reloj::hora=hora; } }

Las operaciones de interfaz serían inútiles si no existiera un

mecanismo que evitara el acceso libre a los atributos de un objeto. La

visibilidad es el mecanismo que nos permite especificar desde dónde

puede ser vista o accedida una propiedad (atributo u operación) de

algún objeto. En C++ esa visibilidad puede especificarse de tres formas:

Pública: El modificador public indica que una propiedad (atributo

u operación) es visible, es decir, puede ser accedida, desde fuera de la

clase.

Privada: El modificador private indica que la propiedad solo

puede ser accedida desde los métodos de la clase.

Protegida: El modificador protected especifica que la propiedad

puede ser vista desde los métodos de la clase y las subclases de esta.

Estos modificadores se escriben antes de la declaración de la

propiedad y mientras no se utilice otro modificador, será el último

indicado el que tomarán las propiedades que se definan debajo de èl.

De manera gráfica al modelar o diseñar una clase podemos

indicar visibilidad pública privada o protegida con los símbolos +, - y #

respectivamente:

Lo más común y seguro es que los atributos de una clase tengan

visibilidad privada y las operaciones (sobre todo las de interfaz) sean

públicas. Si un atributo es privado y se quiere acceder a él desde fuera

de la clase se genera un error en tiempo de compilación. Por ejemplo, si

el atributo hora es privado y se quiere ejecutar la sentencia:

rolex.hora = 365;

Se tendría un error ya que el atributo no podría ser accedido

desde fuera de la clase porque dicho atributo es privado, lo que

obligaría a quien quisiera asignar un valor al atributo a utilizar la

operación de interfaz adecuada (en este caso ponerHora() que si es

pública) y si esta tiene una validación interna para evitar asignaciones

lógicamente incorrectas, no se lograría violar la integridad del objeto.

Otra característica importante que debe incluirse en la definición

de una clase son sus constructores. Un constructor, es un conjunto de

instrucciones diseñadas para inicializar una instancia de la clase (un

objeto). Los parámetros de los constructores se pasan de la misma

forma que los de los métodos. Un constructor se ejecuta

Reloj

- hora : int

- min : int

- seg :int

+ inicializar(h, m, s : int) : void

+ obtTiempo() : string

+ avanzar1Seg() : void

automáticamente cuando se crea un objeto de la clase por lo que su

nombre siempre debe ser idéntico al de la clase. Los constructores no

tienen valores de retorno, ni se heredan.

Cada clase tiene al menos un constructor. Si no se escribe

ninguno, el lenguaje C++ se encargará de suministrarlo. En este caso el

constructor no tiene argumentos y su cuerpo está vacío. A este

constructor se le conoce como constructor por defecto o

predeterminado. Si se agrega la declaración de un constructor a una

clase que no tenía ningún constructor explicito, se pierde el constructor

predeterminado.

Es importante utilizar constructores para asignar valores iniciales al

estado del objeto. En nuestro ejemplo, agregamos una operación

llamada inicializar que realiza tal función, sin embargo, es necesario

llamarla explícitamente en algún momento de la ejecución del

problema para que se ejecute, Por ejemplo:

Reloj rolex; rolex.inicializar(23,0,0);

Qué pasaría si el usuario de nuestra clase olvida llamar a la

función inicializar? Simplemente los atributos hora, min y seg no tendrían

valores iniciales. Si definimos un constructor que desplace a la

operación inicializar() de la siguiente manera:

Reloj::Reloj(int h, int m, int s){ hora=h; min = m; seg = s; }

Podemos construir nuestro objeto rolex con la siguiente sentencia

sin llamar a ninguna operación para inicializarlo pues el constructor se

ejecutaría automáticamente en el mismo momento de la creación:

Reloj rolex(10,25,59);

Por esa razón los valores de los argumentos se envían en la misma

sentencia de creación del objeto.

A continuación presento la versión 2 de la clase Reloj

incorporando todos los detalles vistos anteriormente:

class Reloj{ private: int hora; int min; int seg; public: Reloj(int h, int m, int s); string obtTiempo(); void avanzar1Seg(); void ponerHora(int hora); int obtHora(); void ponerMin(int min); int obtMin(); void ponerSeg(int seg); int obtSeg(); }; Reloj::Reloj(int h, int m, int s){ hora=h; min = m; seg = s; } string Reloj::obtTiempo(){ char tiempo [16]; sprintf (tiempo, "%d:%d:%d", hora, min, seg); return tiempo; } void Reloj::avanzar1Seg(){ if (seg < 59){ seg++; } else{ seg=0; if (min < 59){ min++; } else{ if(hora < 23){ hora++; } else{ hora=0; } } } } void Reloj::ponerHora(int hora){ Reloj::hora=hora; } int Reloj::obtHora(){ return (hora); } void Reloj::ponerMin(int min){ Reloj::min=min; } int Reloj::obtMin(){ return (min); } void Reloj::ponerSeg(int seg){ Reloj::seg=seg; } int Reloj::obtSeg(){ return (seg); }

Atributos

Constructor explícito

Operaciones de interfaz

Por último, es posible que los atributos de un objeto sean objetos

de otra clase; en otras palabras, es posible generar un tipo de objeto

nuevo agrupando objetos existentes. De esta manera se pueden armar

estructuras complejas en un programa, escondidas detrás de la

simplicidad de objetos. También es posible extender las características

de las clases para dar origen a nuevas clases especializadas… Pero eso

es parte del siguiente tema.