Foros del Web » Programación para mayores de 30 ;) » C/C++ »

Problemas con Templates

Estas en el tema de Problemas con Templates en el foro de C/C++ en Foros del Web. Buenas a todos/as Estoy intentando implementar una lista doblemente enlazada y, como la voy a utilizar con distintos tipos de datos, he pensado crear una ...
  #1 (permalink)  
Antiguo 30/11/2007, 10:05
 
Fecha de Ingreso: noviembre-2005
Ubicación: Alicante (España)
Mensajes: 242
Antigüedad: 18 años, 6 meses
Puntos: 1
Problemas con Templates

Buenas a todos/as

Estoy intentando implementar una lista doblemente enlazada y, como la voy a utilizar con distintos tipos de datos, he pensado crear una plantilla.

Hasta ahora he conseguido crear la clase nodo y la clase lista, ambas plantillas de un tipo genérico. SIn embargo, cuando trato de introducir un objeto en el Nodo el compilador se queja de que la conversión del tipo de datos es incorrecto.

Este es el código que tengo:

Nodo.h

//---------------------------------------------------------------------------
#ifndef NodoH
#define NodoH


/* Utilizamos una Plantilla para definir una lista genérica.
De esta forma, es posible almacenar en la lista cualquier tipo de dato
u objeto. */
template<class TIPO> class Lista;
template <class TIPO>

class Nodo {

protected:

TIPO objeto;
Nodo <TIPO> *siguiente;
Nodo <TIPO> *anterior;

friend class Lista<TIPO>;

public:

// Constructor Vacío
Nodo();
// Constructor
Nodo(TIPO obj, Nodo<TIPO>*sig = NULL, Nodo<TIPO>*ant = NULL):
objeto(obj), siguiente(sig), anterior(ant) {}
TIPO daObjeto();
};


Nodo.cpp

//---------------------------------------------------------------------------
#pragma hdrstop
#include "Nodo.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)

template <class TIPO>
// Constructor Vacío
Nodo<TIPO>::Nodo() {
this->objeto = NULL;
this->siguiente = NULL;
this->anterior = NULL;
}

template <class TIPO>
TIPO Nodo<TIPO>::daObjeto() {
return objeto;
}



Lista.h

//---------------------------------------------------------------------------
#ifndef ListaH
#define ListaH
#include "Nodo.h"

template <class TIPO>

class Lista {

protected:

Nodo<TIPO> *inicio;
Nodo<TIPO> *fin;

public:

Lista():inicio(NULL),fin(NULL) {}
~Lista();

void insertarAlPrincipio(TIPO); // Inserta al principio de la lista
void insertarAlFinal(TIPO); // Inserta al final de la lista
bool isListaVacia();
int eliminarNodo(TIPO); // Borra uno o mas nodos
void eliminarNodos(); // Borra todos los nodos
TIPO daInicio();


};
//---------------------------------------------------------------------------
#endif



Lista.cpp

//---------------------------------------------------------------------------
#pragma hdrstop
#include "Lista.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)

// Destructor de la lista
template <class TIPO>
Lista<TIPO>::~Lista () {
Nodo<TIPO> *aux;
// Desde el primer nodo hasta el último
while(inicio) {
aux = inicio;
inicio = inicio->siguiente;
delete (aux);
}
}

template <class TIPO>
// Función que devuelve TRUE si la Lista está vacía o FALSE en caso contrario.
bool Lista<TIPO>::isListaVacia() {
if inicio == NULL return TRUE;
else return FALSE;
}


template <class TIPO>
// Insertar Nodo al Principio de la lista
void Lista<TIPO>::insertarAlPrincipio(TIPO objeto){
// Se reserva memoria para el Nodo y su contenido
Nodo<TIPO> *nodoInicio = new Nodo<TIPO>(objeto);
// Si no hay ningún nodo en la lista se añade al principio sin más.
if (this->inicio == NULL) {
this->inicio = nodoInicio;
this->fin = nodoInicio;
// Si ya hay uno o más nodos, se introduce al principio sin perder al resto.
}else {
//inicio->siguiente->anterior = nodoInicio;
nodoInicio->siguiente = inicio->siguiente;
inicio->siguiente = nodoInicio;
}
}

template <class TIPO>
TIPO Lista<TIPO>::daInicio() {
return this->inicio;
}



Y luego tengo el main:

#include <iostream.h>
#include "Cliente.h"
#include "Lista.cpp"

int main(int argc, char* argv[])
{
int stop;
Cliente *cliente = new Cliente("48366038","Baltasar","Sanchez","Torregros a","Alboraya 40", "Elche", "Alicante", "666503874", 31, 1);
Nodo *nodo = new Nodo(cliente);
Lista <Nodo> lista;
lista.insertarAlPrincipio(*nodo);
cout << "DNI" << lista.daInicio().daDNI();
cin >> stop;


return 0;
}
//---------------------------------------------------------------------------



Tengo dos dudas:

1. En el Main.cpp tengo que incluir el fichero Lista.cpp para que el Linker no proteste. Al principio había puesto #include "Lista.h" pero la aplicación no se ejecutaba y el Linker me daba un error indicando que no encontraba los métodos de la clase Lista. Es algo extraño porque, el fichero está añadido al Proyecto y, si incluyo Lista.h, debería poder acceder al código de las funciones.
Al escribir #inlude "Lista.cpp" ya no protesta pero me gustaría saber la razón

2. En el Main creo un objeto Cliente para añadirlo a la Lista. Realmente tendría que añadirlo al Nodo y este a la Lista pero, con el uso genérico del template, entiendo que puedo hacerlo así... La verdad es que me da un error de compilación al tratar de mostrar el DNI... Y el error lo da en la función daInicio() de la clase Lista (Lista.cpp)...

¿Alguien puede decirme qué estoy haciendo mal?... ¿Cómo puedo implementar una plantilla para crear listas enlazadas e introducir objetos de otras clases en ellas?...

Un saludo.
  #2 (permalink)  
Antiguo 02/12/2007, 15:40
Avatar de Solenbum  
Fecha de Ingreso: noviembre-2007
Mensajes: 45
Antigüedad: 16 años, 6 meses
Puntos: 0
Re: Problemas con Templates

Sobre lo primero, poco puedo aportar. Yo trabajo en linux con Gcc/++ compilando proyectos con el tipico script makefile. ¿como trabjas tu?

Sobre el resto, veamos si puedo ayudar algo, creo que lo que diré aportará mas bien poco.


Tu ultima pregunta resulta un cuanto menos curiosa viendo todo lo escrito anterior, jeje.

Aquí tienes un template de "listas enlazadas" hecho en c++:
http://conclase.net/c/edd/index.php?cap=001h#1_11

Por cierto, lo que escribis en el main:
Cliente *cliente = new Cliente("48366038","Baltasar","Sanchez","Torregros a","Alboraya 40", "Elche", "Alicante", "666503874", 31, 1);
Nodo *nodo = new Nodo(cliente);
Lista <Nodo> lista;

Tomando el ejemplo que de el enlace, sería mas "estetico" quizas el que declares una estructura "Cliente" (sí, struct, en un .h aparte si quieres) en el cual le pasas en 1 procedimiento interno los datos para inicializar sus campos de datos (cadenas por ejemplo) y luego ese tipo de dato lo insertas en la lista, quedando:

Lista<Cliente> lis;
Cliente c("dato1","dato",...);
lis.insertar(c);

Y que todo lo relacionado con el nodo lo haga internamente en la lista, y asi no tienes que crear nada fuera de ella (ese new nodo en el main). (incluso en el ejemplo de arriba puedes "descomponer" el nodo viendo que tu tienes la lista-nodo de forma modular separada)
(no entendí mucho tu diseño e implementación de nodo y lista :( comparado con la forma generica del ejemplo del enlace)

Espero que se entienda mi idea, suerte.
Atención: Estás leyendo un tema que no tiene actividad desde hace más de 6 MESES, te recomendamos abrir un Nuevo tema en lugar de responder al actual.
Respuesta




La zona horaria es GMT -6. Ahora son las 02:44.