Dpto. O.E.I. – U.P.M. ALGORÍTMICA 06/JUL/12 1º) (3’5 Puntos) El juego denominado Migada es un solitario que consiste en ordenar ascendentemente un vector de N números enteros positivos. Las reglas para realizar una jugada son las siguientes: • Se selecciona una de las N posiciones del vector • Se intercambia el valor de la posición seleccionada con el valor de la siguiente posición. • Si la posición seleccionada es la última, se intercambia el contenido de dicha posición con el de la primera posición. Se pide: Desarrollar un algoritmo que recibiendo un vector de N números enteros positivos determine si existe solución del solitario Migada en menos de 20 jugadas. PROGRAM Migada; CONST N = ...; Jugadas = 19; TYPE TIndice = 1 .. N; TSolitario = ARRAY[TIndice] OF Integer; VAR Solitario : TSolitario; Solucion : Boolean; PROCEDURE HacerJugada(VAR Solitario : TSolitario; Pos1 : TIndice); VAR Pos2 : TIndice; Aux : Integer; BEGIN Pos2 := Pos1 MOD N + 1; Aux := Solitario[Pos1]; Solitario[Pos1] := Solitario[Pos2]; Solitario[Pos2] := Aux; END; FUNCTION EsSolucion(Solitario : TSolitario) : Boolean; VAR I : TIndice; Correcto : Boolean; BEGIN Correcto := True; I := 1; WHILE (I < N) AND Correcto DO BEGIN Correcto := Solitario[I] < Solitario[I + 1]; I := I + 1; END; EsSolucion := Correcto END; Universidad Politécnica de Madrid – E.U. Informática Página 1 PROCEDURE TieneSolucion(Solitario : TSolitario; NumJugada : Integer; VAR Solucion : Boolean); VAR Posibilidad : 0 .. N; BEGIN Posibilidad := 0; REPEAT Posibilidad := Posibilidad + 1; HacerJugada(Solitario, Posibilidad); IF EsSolucion(Solitario) THEN Solucion := True ELSE BEGIN IF NumJugada < Jugadas THEN TieneSolucion(Solitario, NumJugada + 1, Solucion); IF NOT Solucion THEN HacerJugada(Solitario, Posibilidad); END UNTIL (Posibilidad = N) OR Solucion; END; BEGIN Solucion := False; TieneSolucion(Solitario, 1, Solucion); Writeln('Solución = ', Solucion) END. Universidad Politécnica de Madrid – E.U. Informática Página 2 2º) (3’5 Puntos) Se define grafo "triconexo" como aquel grafo que es fuertemente conexo aunque se eliminen dos vértices cualquiera del mismo. Se pide: Codificar un algoritmo en Pascal que determine si un grafo no dirigido, implementado con una matriz de adyacencia, es "triconexo". Program EjercicioTriconexo1; CONST N = …; Infinito=MaxInt; TYPE TVertice=1..N; TGrafo=ARRAY[TVertice,TVertice] OF Boolean; TVisitados=ARRAY[TVertice] OF Boolean; VAR G : TGrafo; Visitados : TVisitados; ... PROCEDURE ProfundidadRecursivo(Grafo:TGrafo;V:TVertice); VAR Aux : TVertice; BEGIN Visitados[V]:=True; FOR Aux:=1 TO N DO IF G[V, Aux] AND NOT Visitados[Aux] THEN ProfundidadRecursivo(Grafo,Aux); END; FUNCTION Triconexo(G:TGrafo) : Boolean; VAR I, J, K : TVertice; Correcto : Boolean; BEGIN IF N < 3 THEN Correcto := False ELSE BEGIN I := 1; Correcto := True; WHILE (I <= N) AND Correcto DO BEGIN J := I + 1; WHILE (J <= N) AND Correcto DO BEGIN FOR K := 1 TO N DO Visitados[K] := False; Visitados[I] := True; Visitados[J] := True; IF I <> 1 THEN K := 1 (* Vértice desde que se lanza el recorrido*) ELSE IF J <> N THEN K := N ELSE K := N - 1; ProfundidadRecursivo(G,K); K := 1; WHILE (K <= N) AND Correcto DO (* Todos Visitados*) BEGIN Correcto := Visitados[K]; K := K + 1; END; J := J + 1; END; I := I + 1; END; END; Triconexo := Correcto END; BEGIN WriteLn('El grafo es triconexo ',Triconexo(G)); END. Universidad Politécnica de Madrid – E.U. Informática Página 3 3º) (3 Puntos) Escribir un algoritmo en Pascal que recibiendo dos árboles binarios determine, con un algoritmo de Divide y Vencerás, si son iguales. Se consideran iguales dos árboles cuando sus recorridos en preorden, orden central y postorden son iguales. Utilice la siguiente declaración: TYPE Tarbol=^Nodo; Nodo=RECORD Clave:Integer; Iz,De:Tarbol END; PROGRAM Ejercicio3; TYPE Tarbol=^Nodo; Nodo=RECORD Clave:Integer; Iz,De:Tarbol END; VAR Arbol1, Arbol2 : TArbol; FUNCTION ArbolesIguales(Arbol1, Arbol2: TArbol): Boolean; VAR CorrectoIzq, CorrectoDer : Boolean; BEGIN IF (Arbol1 = NIL) AND (Arbol2 = NIL) THEN ArbolesIguales := True ELSE IF (Arbol1 <> NIL) AND (Arbol2 <> NIL) THEN IF Arbol1^.Clave = Arbol2^.Clave THEN BEGIN CorrectoIzq := ArbolesIguales(Arbol1^.Iz, Arbol2^.Iz); CorrectoDer := ArbolesIguales(Arbol1^.De, Arbol2^.De); ArbolesIguales := CorrectoIzq AND CorrectoDer END ELSE ArbolesIguales := False ELSE ArbolesIguales := False END; BEGIN Writeln('Arboles iguales ',ArbolesIguales(Arbol1,Arbol2)) END. Universidad Politécnica de Madrid – E.U. Informática Página 4