Sei sulla pagina 1di 10

Listas Multienlace

Ejercicio prctico con listas doble-enlace.

Enunciado
Una empresa dispone de una lista de empleados. De cada empleado se conoce: nro. de empleado, apellido y nombre, profesin, cdigo de departamento al que pertenece, sueldo bsico y antigedad. Dicha lista est ordenada por Nro. de Empleado (orden principal); pero tambin puede accederse en forma ordenada por cdigo de departamento (orden secundario). Se pide: Implementar un mdulo que elimine de la lista el empleado con nro. X (donde X viene por parmetro).

Declaracin de tipos
TEmpleado = record nro: integer; nombre: string; profesion: string; depto.: integer; sueldo: real; antiguedad: integer; end; ListaEmpleado = ^Nodolista; Nodolista = record Dato: TEmpleado; Sig_nro: ListaEmpleado; Sig_depto: ListaEmpleado; End; ListaDobleEnlace = record Pri_nro: ListaEmpleado; Pri_depto: ListaEmpleado; End;

Implementar un mdulo que elimine de la lista el empleado con nro. X (donde X viene por parmetro).
Ant_1 Act_1

Pri_nro

Pri_depto

1 5

8 2

10

11

15 2

N I L

16

N I L

Ant_2 Act_2 Criterio Nro. Empleado Criterio Nro. departamento

Ejemplo: eliminar el empleado nmero 10

1. Buscar nodo a eliminar 2. Si encontr 3. Re-enganche orden nro (2 casos) 4. Re-enganche orden depto (2 casos) 5. DISPOSE

Implementar un mdulo que elimine de la lista el empleado con nro. X (donde X viene por parmetro).
Procedure eliminar_empleado_nroX(var ld: ListaDobleEnlace; X: integer; var ok: boolean); var elim: ListaEmpleado; begin elim:= Buscar_NroEmple_OrdenNumero (ld.pri_nro, X); if (elim <> nil) then begin Desenganchar_ptro_ordenNro(ld.Pri_nro, elim); // desenganchar orden nro Desenganchar_ptro_ordenDepto(ld.Pri_depto, elim); //desenganchar orden depto Dispose(elim); //libero espacio Ok:=true; function Buscar_NroEmple_OrdenNumero(pri_nro: ListaEmpleado; End X:integer): ListaEmpleado; Else Ok:= false; var end; act: ListaEmpleado; begin act:= pri_nro; while ((act <> nil) and (act^.dato.nro < X) ) do act:= act^.sig_nro; if (act <> nil) and (act^.dato.nro = X) then Buscar_NroEmple_OrdenNumero:= act else Buscar_NroEmple_OrdenNumero:= nil; end;

Implementar un mdulo que elimine de la lista el empleado con nro. X (donde X viene por parmetro).
Procedure eliminar_empleado_nroX(var ld: ListaDobleEnlace; X: integer; var ok: boolean); var elim: ListaEmpleado; begin elim:= Buscar_NroEmple_OrdenNumero (ld.pri_nro, X); if (elim <> nil) then begin Desenganchar_ptro_ordenNro(ld.Pri_nro, elim); // desenganchar orden nro Desenganchar_ptro_ordenDepto(ld.Pri_depto, elim); //desenganchar orden depto Dispose(elim); //libero espacio Ok:=true; End Desenganchar (orden por numero) Else Ok:= false; end; Ubicarse al principio de la lista.

Mientras (actual no apunta al nodo a eliminar) actualizo el puntero anterior actualizo el puntero actual Si (es el primer elemento) entonces avanzo el puntero inicial Sino realizo enganche del nodo anterior con el siguiente de actual

Implementar un mdulo que elimine de la lista el empleado con nro. X (donde X viene por parmetro).
procedure Desenganchar_ptro_ordenDepto (var pri_depto: ListaEmpleado; buscado: ListaEmpleado); var act, ant: ListaEmpleado; begin act:= pri_depto; ant:= pri_depto; while (act <> buscado ) do begin //se sabe que existe ant:= act; act:= act ^.sig_depto; end; if ( act = pri_depto ) then 2 casos: pri_depto:= act^.sig_depto Eliminar el primero else Medio / final ant^.sig_depto:= act^.sig_depto; end; Cdigo similar para Desenganchar_ptro_ordenNro pero recibiendo pri_nro y usando los punteros sig_nro

Solucin Alternativa
Procedure eliminar_empleado_nroX(var ld: ListaDobleEnlace; X: integer; var ok: boolean); var elim: ListaEmpleado; begin Buscar_Desenganchar_OrdenNumero(ld.pri_nro, elim, X); if (elim <> nil) then begin //llamar a desenganchar por orden depto (igual que antes) Desenganchar_ptro_ordenDepto(ld.Pri_depto, elim); //libero espacio Dispose(elim); Ok:=true; End Else Ok:= false; Recorro el orden por nmero una sola vez. end;

Solucin Alternativa
procedure Buscar_Desenganchar_OrdenNumero(var pri_nro: ListaEmpleado; var buscado: ListaEmpleado; X: integer); var act, ant: ListaEmpleado; begin act:= pri_nro; ant:= pri_nro; while (act <> nil) and (act^.dato.nro < X) do begin ant:= act; act:= act ^.sig_nro; end; if (act <> nil) and (act^.dato.nro = X) then begin //encontro el dato ? buscado:= act; //elimina el enlace if ( act = pri_nro) then pri_nro:= act^.sig_nro else ant^.sig_nro:= act^.sig_nro; end else // no encontr el dato MDULO: Desenganchar_ordenNro (pri_nro, act, ant); buscado:= nil; End;

Discutir
Implementar un mdulo que elimine de la lista

todos los empleados que tengan ms de X aos de antigedad (donde X viene por parmetro).
Qu orden elijo para empezar el recorrido? IDEA

Potrebbero piacerti anche