You are on page 1of 63

Programación Dinámica

Algoritmos y Estructuras de Datos

Company

LOGO

Agenda

1.
1.Punteros
Punteros
2.
2. Estructuras
Estructurasautoreferenciadas
autoreferenciadas
3.
3.Asignación
Asignacióndinámica
dinámicade
dememoria
memoria
4.
4.Listas
Listasenlazadas,
enlazadas, Pilas
PilasyyColas
Colas

Punteros
Su valor es una
dirección de
memoria.

Las variables
normales contienen
un valor específico.

Los punteros
almacenan la
dirección de una
variable que tiene
un valor específico.

Sirven para simular
parámetros por
referencia.

Punteros .

Se pueden definir punteros hacia cualquier tipo de dato. .Declarar punteros Sintaxis Definir *mi_puntero como Entero. Definición Declara un puntero hacia un Entero.

5. un_puntero <. un_numero <.&un_numero.Punteros y operadores Operador de dirección (&) Devuelve la dirección de memoria del operando Ejemplo Declarar un_numero como Entero. Declarar *un_puntero como Entero. //un_puntero obtiene la dirección de un_numero .

Punteros y operadores .

*un_puntero nos devolvería un_numero. //Ahora el valor de un_numero es 7 .Punteros y operadores Operador de indirección(*) Nos permite obtener el valor almacenado en la dirección que tiene asignada. dado que un_puntero apunta hacia un_numero. Ejemplo Para asignar: *un_puntero <.7.

El ejemplo .

) Definir una_carta como carta. Equivalente a: Escribir (*puntero_carta).Punteros y Estructuras Operador punto (.signo. Operador flecha (<-) Definir *puntero_carta como carta. Escribir una_carta.&una_carta. puntero_carta <.signo. Escribir puntero_carta->signo. .

Pilas Colas • Inserciones y • Inserciones eliminaciones en la parte sólo en la posterior y parte superior.Estructuras de Datos Dinámicas Crecen o se contraen durante la ejecución Listas enlazadas • Inserciones y eliminaciones sin restricciones. Árboles binarios • Búsqueda y ordenamiento de alta velocidad y eliminación de duplicados eficiente . eliminaciones en la parte superior.

Estas estructuras terminan con un puntero NULO. Pueden enlazarse mutuamente.Estructura auto-referenciada Contienen un puntero a otra estructura Esta otra estructura es del mismo tipo. . Lo que permite formas estructuras de datos.

Estructura auto-referenciada .

FinEstructura Enlace Es el vínculo entre un nodo y otro. puntero_siguiente apunta hacia un dato del tipo nodo. Definir *puntero_siguiente como nodo.Estructura auto-referenciada Sintaxis Estructura nodo Definir dato como Entero. .

Definir *puntero_nodo como nodo. reservar(puntero_nodo). liberar(puntero_nodo). Función reservar() Reserva memoria para un puntero.Asignación dinámica de memoria Definición Obtiene y libera memoria durante la ejecución del programa. . Función liberar() Libera la memoria reservada por la función reservar.

. llamadas nodos.Listas enlazadas Colección lineal de estructuras autoreferenciadas. Se acceden Los El último mediante siguientes elemento un puntero nodos se tiene como al primer acceden a enlace un elemento través de puntero de la lista. NULO. los enlaces. conectadas por enlaces mediante punteros.

circulares. Comienzan con un puntero al primer nodo. es fácil mantenerla ordenada. soporta un número indeterminado de elementos.Listas enlazadas A diferencia de un vector. A diferencia de un vector. terminan en puntero nulo y se recorren en una dirección . dobles. etc. Nosotros trabajaremos con LISTAS ENLAZADAS SIMPLES Existen varios tipos: Simples.

  Debe permitir ingresar caracteres en la lista en orden alfabético.Un problema  Diseñe un algoritmo que permita manipular una lista de caracteres. Debe permitir eliminar cualquier carácter de la lista. .

Plan de acción El usuario ingresa una opción En caso la opción sea 1. se ejecuta el procedimiento de inserción En caso la opción sea 2. se termina la ejecución del programa . se ejecuta el procedimiento de eliminación • Sólo si la lista no está vacía En caso la opción sea 3.

Estructura jerárquica Módulo Principal Insertar carácter en orden Eliminar carácter Verificar que lista esté vacía Mostrar contenido de la lista .

Definir *puntero_siguiente FinEstructura como nodo_lista.Definir Estructuras Nodo en Lista Enlazada Estructura nodo_lista Definir caracter como Caracter. .

caracter_ingresado).esta_vacia(puntero_inicio). FinMientras FinProceso . Si ~es_una_lista_vacia Entonces Leer caracter_ingresado.Módulo Principal Proceso principal Definir *puntero_inicio como nodo_lista. 2: es_una_lista_vacia <. insertar(puntero_inicio. caracter_eliminado <. Mientras opcion <> 3 Hacer Segun opcion Hacer 1: Leer caracter_ingresado. FinSi FinSegun Leer opcion.suprimir(puntero_inicio. //Variables para opción y caracteres ingresados Leer opcion. caracter_ingresado).

Insertar elemento .

En caso esté al medio. la inserción se realiza modificando las direcciones de los punteros. hay que cambiar el valor del puntero al primer nodo.Insertar elemento Reservar memoria para el nuevo nodo Ubicar entre que nodos hay que colocar el nuevo elemento recién creado En caso haya colocarlo en primera posición. .

Definir *puntero_actual como nodo_lista.puntero_actual. puntero_previo <.puntero_actual->puntero_siguiente.NULO.Insertar elemento SubProceso insertar (puntero_inicio por Referencia. puntero_nuevo->puntero_siguiente <. FinSi FinSubProceso . puntero_nuevo->caracter <.caracter. Definir *puntero_previo como nodo_lista. reservar(puntero_nuevo).puntero_nuevo. puntero_inicio <.puntero_nuevo. Mientras (puntero_actual <> NULO & caracter > puntero_actual->caracter) Hacer puntero_previo <.puntero_inicio. caracter por Valor) Definir *puntero_nuevo como nodo_lista.NULO. puntero_actual <.puntero_inicio. Sino puntero_previo->puntero_siguiente <. puntero_actual <. puntero_nuevo->puntero_siguiente <. FinMientras Si puntero_previo = NULO Entonces puntero_nuevo->puntero_siguiente <.puntero_actual.

Eliminar elemento .

es necesario cambiar el puntero al primer nodo.Eliminar elemento La eliminación implica remover los enlaces al nodo a eliminar Al eliminar. necesitamos liberar la memoria reservada para el nodo eliminado. Si el carácter a eliminar está en la primera posición. . Debemos informar al programa si el nodo a eliminar fue encontrado en la lista.

caracter.puntero_actual.caracter. Si caracter = puntero_inicio->caracter Entonces auxiliar <.puntero_inicio. Mientras puntero_actual <> NULO & puntero_actual->caracter <> caracter Hacer puntero_previo <.puntero_inicio<-puntero_siguiente. FinSi FinSi FinFuncion . *puntero_actual. puntero_actual <.puntero_actual->siguiente. caracter_eliminado <.suprimir (puntero_inicio por Referencia.puntero_actual. liberar(auxiliar). puntero_previo->puntero_siguiente <. caracter_eliminado <. FinMientras Si puntero_actual <> NULO Entonces auxiliar <.Eliminar elemento Funcion caracter_eliminado <. *auxiliar como nodo_lista. puntero_inicio <. Sino puntero_previo <.puntero_actual->puntero_siguiente. liberar(auxiliar). caracter por Valor) Definir *puntero_previo.puntero_inicio. puntero_actual <.puntero_inicio->siguiente.

Sino Mientras puntero_actual <> NULO Hacer Escribir puntero_actual->caracter. FinMientras Escribir "NULO". puntero_actual <. FinSi FinSubProceso .Mostrar contenido SubProceso mostrar_lista(puntero_actual) Si puntero_actual = NULO Entonces Escribir "La lista está vacía". "-->".puntero_actual->puntero_siguiente. Sin Saltar.

esta_vacia(puntero_inicio) Definir resultado como Logico.puntero_inicio = NULO. resultado <.¿Está vacía? Funcion resultado <. FinFuncion .

es una lista enlazada con restricciones .Pilas Los nodos sólo se agregan en el extremo superior. Los nodos sólo se eliminan en el extremo superior. Como en los platos en un Buffet Modo de acceso: LIFO La base de la pila es un enlace a NULO. En conclusión.

Pilas Apilar Desapilar • Agrega un nuevo • Remueve un nodo en la parte nodo de la parte superior de la pila superior de la pila • Retorna el valor retirado .

Una pila de enteros Módulo Principal Apilar Desapilar Verificar si está vacía Mostrar en pantalla .

Pilas .

.Definir Estructuras Nodo en Pila Estructura nodo_pila Definir dato como Entero. Definir *puntero_siguiente FinEstructura como nodo_pila.

Módulo Principal Proceso principal Definir *puntero_pila como nodo_pila.NULO. mostrar_pila(puntero_pila). 2: Si ~esta_vacia(puntero_pila) Entonces Escribir desapilar(puntero_pila). FinMientras FinProceso . Leer opcion. Mientras opcion <> 3 Hacer Segun opcion Hacer 1: Leer valor_ingresado. valor_ingresado). FinSegun Leer opcion. apilar(puntero_pila. FinSi mostrar_pila(puntero_pila). //Declarar variables adicionales puntero_pila <.

Apilar elemento .

puntero_nuevo.dato. puntero_pila <. reservar(puntero_nuevo). dato por Valor) Definir *puntero_nuevo como nodo_pila.Apilar elemento SubProceso apilar (puntero_pila Por Referencia. puntero_nuevo->dato <. puntero_nuevo->puntero_siguiente <.puntero_pila. FinSubProceso .

Des-apilar elemento .

FinSubProceso . liberar(auxiliar).puntero_pila.puntero_pila->dato. auxiliar <.Des-apilar elemento SubProceso desapilar(puntero_pila por Referencia) Definir *auxiliar como nodo_pila.puntero_pila->puntero_siguiente. Definir valor_desapilado como Entero. valor_desapilado <. puntero_pila <.

FinSi FinSubProceso . Mientras puntero_actual <> NULO Hacer Escribir puntero_actual->dato. "-->".puntero_actual->puntero_siguiente.Mostrar Pila SubProceso mostrar_pila(puntero_actual) Si puntero_actual = NULO Entonces Escribir "La pila está vacía \n". Sino Escribir "Contenido de la pila: ". puntero_actual <. FinMientras Escribir "NULO".

resultado <.esta_vacia(puntero_inicio) Definir resultado como Logico.¿Está vacía? Funcion resultado <. FinFuncion .puntero_inicio = NULO.

Colas Imaginen un cajero de supermercado. Útiles en. colas de impresión. La base de la pila es un enlace a NULO. . por ejemplo. Los nodos sólo se eliminan sólo del inicio. Los nodos se ingresan sólo al final. Modo de acceso: FIFO.

Colas Encolar Desencolar • Para ingresar • Para remover elementos elementos .

Una cola de caracteres Módulo Principal Encolar Desencolar Verificar si está vacía Mostrar en pantalla .

Colas .

FinEstructura .Definir Estructuras Nodo en Cola Estructura nodo_cola Definir dato como Caracter. Definir *puntero_siguiente como nodo_cola.

Módulo Principal
Proceso principal
Definir *puntero_inico como nodo_cola;
Definir *puntero_fin como nodo_cola;
//Declarar variables adicionales
puntero_inicio <- NULO;
puntero_fin <- NULO;
Leer opcion;
Mientras opcion <> 3 Hacer
Segun opcion Hacer
1:
Leer valor_ingresado;
encolar(puntero_inicio, puntero_fin, valor_ingresado);
mostrar_contenido(puntero_inicio);
2:
Si ~esta_vacia(puntero_inicio) Entonces
Escribir desencolar(puntero_inicio, puntero_fin);
FinSi
mostrar_contenido(puntero_inicio);
FinSegun
Leer opcion;
FinMientras
FinProceso

Encolar

Encolar
Reservamos memoria para el nuevo nodo

Si la cola está vacía, el puntero de inicio debe
apuntar hacia el nuevo nodo
Si la cola no está vacía, el último nodo debe
apuntar hacia el nuevo nodo
Finalmente, el puntero de fin debe de apuntar
ahora hacia el nuevo nodo

dato Por Valor) Definir *puntero_nuevo como nodo_cola.NULO.puntero_nuevo. FinSi puntero_fin <. reservar(puntero_nuevo). Sino puntero_fin->puntero_siguiente <.puntero_nuevo. puntero_nuevo->dato <.dato. Si esta_vacia(puntero_inicio) Entonces puntero_inicio <. FinSubProceso . puntero_nuevo->puntero_siguiente <.Encolar SubProceso encolar(puntero_inicio Por Referencia. puntero_fin Por Referencia.puntero_nuevo.

Desencolar .

El puntero de inicio ahora apunta hacia el segundo nodo de la cola.Desencolar Extraer el dato del primer nodo de la cola. . Si la cola queda vacía. debemos modificar el valor del puntero fin. Liberamos la memoria del nodo removido mediante la variable auxiliar.

Mostrar contenido SubProceso mostrar_contenido(puntero_actual) Si puntero_actual = NULO Entonces Escribir "La cola está vacía". puntero_actual <. FinSi FinSubProceso . Mientras puntero_actual <> NULO Hacer Escribir puntero_actual->dato. Sino Escribir "La cola contiene: ". " --> ".puntero_actual->puntero_siguiente. FinMientras Escribir " NULO".

resultado <.¿Está vacía? Funcion resultado <.puntero_inicio = NULO.esta_vacia(puntero_inicio) Definir resultado como Logico. FinFuncion .

Un Problema  Para un grupo de n productos se desea almacenar en una LISTA los siguientes datos: código. descripción y cantidad total solicitada. ordenado en forma creciente respecto al código.  Nota: En la LISTA algunos productos se pueden repetir . se pide presentar un listado que muestre el código del producto. código de cliente. descripción. cantidad solicitada.  Luego en base a la LISTA.

Un problema Productos de Entrada: Código Descripción Cantidad Código de Cliente 201 Lápiz 500 820 105 Borrador 100 515 201 Lápiz 100 806 Reporte de Salida: Código Descripción Cantidad 105 Borrador 100 201 Lápiz 600 .

Plan de acción Definir estructuras de datos Agregar las ventas a la lista enlazada • En orden de código de producto Calcular las cantidades acumuladas por cada producto y mostrar el reporte. .

Definir cantidad como Entero. Definir *puntero_siguiente como nodo_lista.Definir Estructuras Venta Estructura venta Definir codigo_producto como Entero. Definir codigo_cliente como Entero. FinEstructura . Dimension descripcion[50]. FinEstructura Nodo en la Lista Estructura nodo_lista Definir dato como venta. Definir descripcion como Caracter.

Una cola de caracteres Módulo Principal Registrar venta Mostrar reporte .

1 Hacer Leer informacion_ingresada. puntero_inicio <. Definir contador_ventas como Entero.descripcion. FinProceso . Para contador_ventas <.NULO. Leer informacion_ingresada.0 Hasta numero_ventas .cantidad.Módulo principal Proceso principal Definir numero_ventas como Entero.codigo_cliente. registrar_venta(puntero_inicio. Definir informacion_ingresada como venta. Leer informacion_ingresada. informacion_ingresada). Definir *puntero_inicio como nodo_lista. Leer numero_ventas. FinPara mostrar_reporte(puntero_inicio). Leer informacion_ingresada.codigo_producto.

Definir *puntero_actual como nodo_lista. puntero_nuevo->puntero_siguiente <. FinSi FinSubProceso . puntero_previo <. puntero_nuevo->dato <.informacion_ingresada.puntero_nuevo.puntero_inicio. informacion_ingresada por Valor) Definir *puntero_previo como nodo_lista.puntero_actual. puntero_nuevo->puntero_siguiente <. reservar(puntero_nuevo). Sino puntero_previo->puntero_siguiente <.puntero_actual->puntero_siguiente. puntero_inicio <.Registrar venta SubProceso registrar_venta(puntero_inicio Por Referencia. FinMientras Si puntero_previo = NULO Entonces puntero_nuevo->puntero_siguiente <.puntero_inicio.NULO.puntero_actual.puntero_nuevo. puntero_actual <.codigo_producto Hacer puntero_previo <.NULO. puntero_actual <. Definir *puntero_nuevo como nodo_lista.codigo_producto > (puntero_actual->dato). Mientras puntero_actual <> NULO & informacion_ingresada.

cantidad.Mostrar reporte SubProceso mostrar_reporte(puntero_inicio) Definir informacion_venta como venta. Mientras puntero_actual <> NULO Hacer informacion_venta <. informacion_previa.puntero_actual->dato. Sino Escribir informacion_previa.codigo_producto = informacion_previa. puntero_actual <. FinSi puntero_actual <.codigo_producto.puntero_actual->puntero_siguiente.cantidad.cantidad <.cantidad.codigo_producto.codigo_producto Hacer informacion_previa. FinMientras Escribir informacion_previa.puntero_actual->puntero_siguiente.puntero_actual->dato. informacion_previa. FinSi FinSubProceso . informacion_previa. Definir informacion_previa como venta. Si puntero_actual <> NULO Hacer informacion_previa <.descripcion.cantidad + informacion_venta.descripcion.informacion_previa. informacion_previa. informacion_previa <.informacion_venta. Si informacion_venta.