fbpx
Wikipedia

Algoritmo de Steinhaus–Johnson–Trotter

El algoritmo Steinhaus–Johnson–Trotter o algoritmo Johnson–Trotter, también llamado cambios simples, es un algoritmo que lleva el nombre de Hugo Steinhaus, Selmer M. Johnson y Hale F. Trotter que genera todas las permutaciones de n elementos. Cada permutación en la secuencia que genera difiere de la permutación anterior al intercambiar dos elementos adyacentes de la secuencia. De manera equivalente, este algoritmo encuentra un ciclo hamiltoniano en el permutoedro. El algoritmo Johnson-Trotter ofrece una forma eficaz de generar directamente permutaciones de la longitud requerida sin calcular permutaciones más cortas.[1]

Historia

Johnson y Trotter descubrieron el algoritmo independientemente el uno del otro a principios de la década de 1960. Un libro de Steinhaus, publicado originalmente en 1958 y traducido al inglés en 1963, describe un rompecabezas relacionado de generar todas las permutaciones mediante un sistema de partículas, cada una moviéndose a una velocidad constante a lo largo de una línea e intercambiando posiciones cuando una partícula adelanta a otra. No hay solución posible para n>3, porque el número de intercambios es mucho menor que el número de permutaciones, pero el algoritmo Steinhaus–Johnson–Trotter describe el movimiento de partículas con velocidades no constantes que generan todas las permutaciones.

Fuera de las matemáticas, el mismo método se conoció durante mucho más tiempo como un método para cambiar el sonido de las campanas de la iglesia: proporciona un procedimiento mediante el cual se puede tocar un conjunto de campanas a través de todas las permutaciones posibles, cambiando el orden de solo dos campanas por cambio. Estos llamados "cambios simples" se registraron ya en 1621 para cuatro campanas, y un libro de 1677 de Fabian Stedman enumera las soluciones para hasta seis campanas. Más recientemente, los timbres de cambio han cumplido con la regla de que ninguna campana puede permanecer en la misma posición durante tres permutaciones consecutivas; esta regla es no sirve para los cambios simples, por lo que se han ideado otras estrategias que intercambian múltiples campanas por cambio.[2]

¿Cómo funciona el algoritmo?

El algoritmo Johnson-Trotter es un algoritmo para calcular permutaciones dado un conjunto de valores. Una permutación es una forma de alterar los valores en un conjunto para crear una secuencia única diferente de la original. Si tenemos el conjunto {1, 2, 3, 4, 5} una permutación sería 2,1,4,5,3 y otra sería 3,4,2,1,5. Usando un peculiar pequeño algoritmo, podemos transponer valores en el conjunto para obtener todas las permutaciones de ese conjunto dado. Podría usar un algoritmo de este tipo para encontrar una palabra que podría estar codificada u obtener una secuencia única dado que el conjunto contiene suficientes valores. 

Existen muchos algoritmos para encontrar permutaciones. El de Steinhaus–Johnson–Trotter es solo uno de muchos, y como todos los algoritmos, tiene sus limitaciones. Pero aunque la comprensión del mismo no es exactamente difícil, contiene algunas reglas que debemos seguir. Cada valor en nuestro conjunto de números recibe una dirección de movilidad. Esto significa que a medida que intercambiamos el valor también tiene una dirección en la que se intercambia.

1) Puede intercambiar con el vecino a la izquierda o derecha inmediata (determinado por su movilidad). Ahora bien, si un valor está en el extremo izquierdo y tiene movilidad hacia la izquierda, se considera inmóvil. Lo mismo con si está en el extremo derecho y tiene derecho a la movilidad. Para empezar, todos los valores han dejado movilidad. 2) El intercambio solo tendrá lugar si el vecino al lado (en la dirección de su movilidad) es menor que el valor que se intercambia. De lo contrario, también se considera bloqueado. Por ejemplo, si 3 y 2 están uno al lado del otro y ambos se mueven hacia la izquierda, no se realiza ningún intercambio hacia la izquierda porque 3 es mayor que 2. Actualmente, 2 está bloqueado en su lugar. Pero si hubiese sido 1 y 4, entonces 4 se intercambiará. 3) Se realiza un intercambio en cada pase. Todos los valores en el conjunto que son de un valor más alto que el valor intercambiado tendrán su dirección de movilidad cambiada a la otra dirección.

En resumen, lo que este algoritmo hace es buscar el valor móvil más alto en el conjunto, luego lo intercambia en la dirección de su movilidad. Si el valor más alto se considera bloqueado, buscará el segundo, tercer y cuarto número más alto y así sucesivamente hasta que no haya más números. Entonces, lo que necesitamos hacer es una forma de 1) encontrar el número móvil más alto actualmente, 2) una rutina para intercambiar los valores en el conjunto y 3) un bucle principal que imprimirá cada uno permutación y continuar hasta que se agoten todas las permutaciones.[3][4]

La complejidad de este algoritmo, usando montículos de Fibonacci en la implementación del algoritmo de Dijkstra, es de O(V2log V + VE): el algoritmo usa un tiempo de O(VE) para la fase Bellman-Ford del algoritmo, y O(V log V + E) para cada una de las V instancias realizadas del algoritmo de Dijkstra. Entonces, cuando el grafo es disperso el tiempo total del algoritmo puede ser menor que el algoritmo de Floyd-Warshall, que resuelve el mismo problema en un tiempo de O(V3).

Aceleración de Even

Una mejora posterior de Shimon Even proporciona una mejora en el tiempo de ejecución al almacenar información adicional para cada elemento en la permutación: su posición y una dirección (positiva, negativa o cero) en la que se está moviendo actualmente (esencialmente, esta es la misma información calculada utilizando la paridad de la permutación en la versión del algoritmo de Johnson). Inicialmente, la dirección del número 1 es cero, y todos los demás elementos tienen una dirección negativa:

1 −2 −3

En cada paso, el algoritmo encuentra el elemento más grande con una dirección distinta de cero y lo intercambia en la dirección indicada:

1 −3 −2

Si esto hace que el elemento elegido alcance la primera o la última posición dentro de la permutación, o si el siguiente elemento en la misma dirección es mayor que el elemento elegido, la dirección del elemento elegido se establece en cero:

3 1 −2

Después de cada paso, todos los elementos mayores que el elemento elegido (que anteriormente tenía la dirección cero) tienen sus direcciones establecidas para indicar el movimiento hacia el elemento elegido. Es decir, positivo para todos los elementos entre el inicio de la permutación y el elemento elegido, y negativo para los elementos hacia el final. Por lo tanto, en este ejemplo, después de que el número 2 se mueve, el número 3 se vuelve a marcar con una dirección:

+3 2 1

Los dos pasos restantes del algoritmo para n=3 son:

2 +3 1 2 1 3

Cuando todos los números quedan sin marcar, el algoritmo termina. Este algoritmo toma tiempo O(i) para cada paso en el que el mayor número para moverse es n-i+1. Por lo tanto, los intercambios que involucran el número n toman solo tiempo constante; Dado que estos intercambios representan todos menos una fracción de 1/n de todos los intercambios realizados por el algoritmo, el tiempo promedio por permutación generada también es constante, aunque un pequeño número de permutaciones llevará una mayor cantidad de tiempo.  Una versión sin bucle más compleja del mismo procedimiento permite que se realice en tiempo constante por permutación en todos los casos; sin embargo, las modificaciones necesarias para eliminar los bucles del procedimiento lo hacen más lento en la práctica.[5]

Interpretación geométrica

El conjunto de todas las permutaciones de n elementos puede representarse geométricamente mediante un permutoedro, el politopo formado a partir del casco convexo de n! vectores, las permutaciones del vector (1,2, ... n). Aunque se define en el espacio n-dimensional, en realidad es un  politopo (n-1)-dimensional. Por ejemplo, el permutoedro en cuatro elementos es un poliedro tridimensional, el octaedro truncado. Si cada vértice del permutoedro está marcado por la permutación inversa a la permutación definida por sus coordenadas de vértice, el etiquetado resultante describe un gráfico de Cayley del grupo simétrico de permutaciones en n elementos, según lo generado por las permutaciones que intercambian pares de elementos adyacentes. Por lo tanto, cada dos permutaciones consecutivas en la secuencia generada por el algoritmo Steinhaus–Johnson–Trotter corresponden de esta manera a dos vértices que forman los puntos finales de un borde en el permutoedro, y toda la secuencia de permutaciones describe un camino hamiltoniano en el permutoedro, un camino que pasa a través de cada vértice exactamente una vez. Si la secuencia de permutaciones se completa agregando una arista más desde la última permutación a la primera en la secuencia, el resultado es un ciclo hamiltoniano.

Relación con los códigos de Gray

Un código Gray para números en una raíz dada es una secuencia que contiene cada número hasta un límite dado exactamente una vez, de tal manera que cada par de números consecutivos difiere en uno en un solo dígito. El n! las permutaciones de los n números del 1 al n se pueden colocar en correspondencia uno a uno con el n! números del 0 al n!-1 emparejando cada permutación con la secuencia de números ci que cuentan el número de posiciones en la permutación que están a la derecha del valor i y que contienen un valor menor que i (es decir, el número de inversiones para el que i es el mayor de los dos valores invertidos), y luego interpretar estas secuencias como números en el sistema de números factoriales, es decir, el sistema de radix mixto con secuencia de radix (1,2,3,4). Por ejemplo, la permutación (3,1,4,5,2) daría los valores c1= 0, c2=0, c3=2, c4=1 y c5=1. La secuencia de estos valores, (0,0,2,1,1), da el número 0 × 0! + 0 × 1! + 2 × 2! + 1 × 3! + 1 × 4! = 34.

Las permutaciones consecutivas en la secuencia generada por el algoritmo Steinhaus–Johnson–Trotter tienen un número de inversiones que difieren en uno, formando un código Gray para el sistema de números factoriales.

En términos más generales, los investigadores de algoritmos combinatorios han establecido un código Gray para un conjunto de objetos combinatorios para que sea un orden de los objetos en los que cada dos objetos consecutivos difieren de la manera mínima posible.[6]

El algoritmo en diferentes lenguajes de programación

JAVA[7]

public class JohnsonTrotter { public static void perm(int n) { int[] p = new int[n]; // permutation int[] pi = new int[n]; // inverse permutation int[] dir = new int[n]; // direction = +1 or -1 for (int i = 0; i < n; i++) { dir[i] = -1; p[i] = i; pi[i] = i; } perm(0, p, pi, dir); StdOut.printf(" (0 1)\n"); } public static void perm(int n, int[] p, int[] pi, int[] dir) { // base case - print out permutation if (n >= p.length) { for (int i = 0; i < p.length; i++) StdOut.print(p[i]); return; } perm(n+1, p, pi, dir); for (int i = 0; i <= n-1; i++) { // swap StdOut.printf(" (%d %d)\n", pi[n], pi[n] + dir[n]); int z = p[pi[n] + dir[n]]; p[pi[n]] = z; p[pi[n] + dir[n]] = n; pi[z] = pi[n]; pi[n] = pi[n] + dir[n]; perm(n+1, p, pi, dir); } dir[n] = -dir[n]; } public static void main(String[] args) { int n = Integer.parseInt(args[0]); perm(n); } } 

C++[8]

#include <cstdlib> using namespace std; struct Arista{ unsigned o; unsigned d; int peso; LAristas sig; }; typedef LAristas Arista*; typedef TGrafo LArista[N]; typedef TVector int[N]; typedef TMatriz TVector[N]; void johnson(const TGrafo &grafo, int ig, TMatriz &distancias, TMatriz &previos){ Arista* p; TVector min_caminos; TVector aux_dist; TVector aux_prev; grafo[ig] = nueva_arista(ig,1,0,NULL); ig++; p = grafo[ig]; for(unsigned i=2; i<=ig-2; i++){ p->sig = nueva_arista(ig,i,0,NULL); p = p->sig; } BellmanFord(grafo,ig, min_caminos); for(unsigned i=1; i<=ig-1; i++){ p = grafo[i]; while(p != NULL){ p->peso = p->peso + min_caminos[p->o] - min_caminos[p->d]; p = p->sig; } } for(unsigned i=1; i<=ig-2; i++){ Dijkstra(grafo,i-1, aux_dist,aux_prev) previos[i-1] = aux_prev; CalcularDistancias(grafo, previos, aux_dist,distancias); } } 

PYTHON[9]

def nobody(): while True: yield False # The term "troll" is taken from Knuth's choice of word def sjt(pi, inv, i, trolls): d = -1 # Directoin. -1 is descending, +1 is ascending. while True: j = inv[i] # j is the position of the current "troll" if pi[j] < pi[j + d]: d = -d yield next(trolls[i - 1]) else: pi[j], pi[j + d] = pi[j + d], pi[j] inv[i] += d inv[pi[j]] -= d yield True def setup(n): # Pad pi with n + 2, so that pi[i] will always be < the two ends. pi = [n + 2] + [i for i in range(1, n + 1)] + [n + 2] inv = pi[:-1] # nobody simply continuously yields False. By adding a "nobody" generator # at both ends of trolls, False is autmatically yieded by sjt when needed. trolls = [nobody()] trolls.extend(sjt(pi, inv, i + 1, trolls) for i in range(n)) trolls += [nobody()] # The lead troll will be the item n in the permutation lead_troll = trolls[-2] return pi, lead_troll def permutations(n): pi, lead_troll = setup(n) yield pi[1:-1] while next(lead_troll): yield pi[1:-1] def cyclic_test(n): pi, lead_troll = setup(n) c = 0 while True: print('Output: ', .join(str(x) for x in pi[1:-1])) c += 1 if not next(lead_troll): print('-------') print(c) print('-------') sleep(1) c = 0 if __name__ == '__main__': print('\n'.join(.join(str(x) for x in pi) for pi in permutations(1))) print('\n'.join(.join(str(x) for x in pi) for pi in permutations(2))) print('\n'.join(.join(str(x) for x in pi) for pi in permutations(3))) print('\n'.join(.join(str(x) for x in pi) for pi in permutations(4))) cyclic_test(3) 

Véase también

Referencias

  1. «Steinhaus–Johnson–Trotter algorithm». Wikipedia (en inglés). 
  2. McGuire, Gary. «Bells, motels and permutation». Lingüística. 
  3. «Johnson-Trotter Algorithm in VC++.NET : The Coders Lexicon». www.coderslexicon.com. 
  4. Levitin, Anany. «Introducción al diseño de algoritmos». Programación. 
  5. Even, Shimon. «Graph Algorithms». Estudio de Algoritmos. 
  6. Savage, Carla (1 de enero de 1997). «A Survey of Combinatorial Gray Codes». SIAM Review 39 (4): 605-629. ISSN 0036-1445. doi:10.1137/S0036144595295272. Consultado el 25 de abril de 2020. 
  7. «JohnsonTrotter.java». 
  8. «Algoritmo de Johnson». Wikipedia, la enciclopedia libre. 20 de abril de 2020. 
  9. «Steinhaus–Johnson–Trotter (SJT) Permutation Generation Algorithm in Python using Coroutines (Generators)». Gist (en inglés). 
  •   Datos: Q4925248

algoritmo, steinhaus, johnson, trotter, algoritmo, steinhaus, johnson, trotter, algoritmo, johnson, trotter, también, llamado, cambios, simples, algoritmo, lleva, nombre, hugo, steinhaus, selmer, johnson, hale, trotter, genera, todas, permutaciones, elementos,. El algoritmo Steinhaus Johnson Trotter o algoritmo Johnson Trotter tambien llamado cambios simples es un algoritmo que lleva el nombre de Hugo Steinhaus Selmer M Johnson y Hale F Trotter que genera todas las permutaciones de n elementos Cada permutacion en la secuencia que genera difiere de la permutacion anterior al intercambiar dos elementos adyacentes de la secuencia De manera equivalente este algoritmo encuentra un ciclo hamiltoniano en el permutoedro El algoritmo Johnson Trotter ofrece una forma eficaz de generar directamente permutaciones de la longitud requerida sin calcular permutaciones mas cortas 1 Indice 1 Historia 2 Como funciona el algoritmo 3 Aceleracion de Even 4 Interpretacion geometrica 5 Relacion con los codigos de Gray 6 El algoritmo en diferentes lenguajes de programacion 7 Vease tambien 8 ReferenciasHistoria EditarJohnson y Trotter descubrieron el algoritmo independientemente el uno del otro a principios de la decada de 1960 Un libro de Steinhaus publicado originalmente en 1958 y traducido al ingles en 1963 describe un rompecabezas relacionado de generar todas las permutaciones mediante un sistema de particulas cada una moviendose a una velocidad constante a lo largo de una linea e intercambiando posiciones cuando una particula adelanta a otra No hay solucion posible para n gt 3 porque el numero de intercambios es mucho menor que el numero de permutaciones pero el algoritmo Steinhaus Johnson Trotter describe el movimiento de particulas con velocidades no constantes que generan todas las permutaciones Fuera de las matematicas el mismo metodo se conocio durante mucho mas tiempo como un metodo para cambiar el sonido de las campanas de la iglesia proporciona un procedimiento mediante el cual se puede tocar un conjunto de campanas a traves de todas las permutaciones posibles cambiando el orden de solo dos campanas por cambio Estos llamados cambios simples se registraron ya en 1621 para cuatro campanas y un libro de 1677 de Fabian Stedman enumera las soluciones para hasta seis campanas Mas recientemente los timbres de cambio han cumplido con la regla de que ninguna campana puede permanecer en la misma posicion durante tres permutaciones consecutivas esta regla es no sirve para los cambios simples por lo que se han ideado otras estrategias que intercambian multiples campanas por cambio 2 Como funciona el algoritmo EditarEl algoritmo Johnson Trotter es un algoritmo para calcular permutaciones dado un conjunto de valores Una permutacion es una forma de alterar los valores en un conjunto para crear una secuencia unica diferente de la original Si tenemos el conjunto 1 2 3 4 5 una permutacion seria 2 1 4 5 3 y otra seria 3 4 2 1 5 Usando un peculiar pequeno algoritmo podemos transponer valores en el conjunto para obtener todas las permutaciones de ese conjunto dado Podria usar un algoritmo de este tipo para encontrar una palabra que podria estar codificada u obtener una secuencia unica dado que el conjunto contiene suficientes valores Existen muchos algoritmos para encontrar permutaciones El de Steinhaus Johnson Trotter es solo uno de muchos y como todos los algoritmos tiene sus limitaciones Pero aunque la comprension del mismo no es exactamente dificil contiene algunas reglas que debemos seguir Cada valor en nuestro conjunto de numeros recibe una direccion de movilidad Esto significa que a medida que intercambiamos el valor tambien tiene una direccion en la que se intercambia 1 Puede intercambiar con el vecino a la izquierda o derecha inmediata determinado por su movilidad Ahora bien si un valor esta en el extremo izquierdo y tiene movilidad hacia la izquierda se considera inmovil Lo mismo con si esta en el extremo derecho y tiene derecho a la movilidad Para empezar todos los valores han dejado movilidad 2 El intercambio solo tendra lugar si el vecino al lado en la direccion de su movilidad es menor que el valor que se intercambia De lo contrario tambien se considera bloqueado Por ejemplo si 3 y 2 estan uno al lado del otro y ambos se mueven hacia la izquierda no se realiza ningun intercambio hacia la izquierda porque 3 es mayor que 2 Actualmente 2 esta bloqueado en su lugar Pero si hubiese sido 1 y 4 entonces 4 se intercambiara 3 Se realiza un intercambio en cada pase Todos los valores en el conjunto que son de un valor mas alto que el valor intercambiado tendran su direccion de movilidad cambiada a la otra direccion En resumen lo que este algoritmo hace es buscar el valor movil mas alto en el conjunto luego lo intercambia en la direccion de su movilidad Si el valor mas alto se considera bloqueado buscara el segundo tercer y cuarto numero mas alto y asi sucesivamente hasta que no haya mas numeros Entonces lo que necesitamos hacer es una forma de 1 encontrar el numero movil mas alto actualmente 2 una rutina para intercambiar los valores en el conjunto y 3 un bucle principal que imprimira cada uno permutacion y continuar hasta que se agoten todas las permutaciones 3 4 La complejidad de este algoritmo usando monticulos de Fibonacci en la implementacion del algoritmo de Dijkstra es de O V2log V VE el algoritmo usa un tiempo de O VE para la fase Bellman Ford del algoritmo y O V log V E para cada una de las V instancias realizadas del algoritmo de Dijkstra Entonces cuando el grafo es disperso el tiempo total del algoritmo puede ser menor que el algoritmo de Floyd Warshall que resuelve el mismo problema en un tiempo de O V3 Aceleracion de Even EditarUna mejora posterior de Shimon Even proporciona una mejora en el tiempo de ejecucion al almacenar informacion adicional para cada elemento en la permutacion su posicion y una direccion positiva negativa o cero en la que se esta moviendo actualmente esencialmente esta es la misma informacion calculada utilizando la paridad de la permutacion en la version del algoritmo de Johnson Inicialmente la direccion del numero 1 es cero y todos los demas elementos tienen una direccion negativa 1 2 3En cada paso el algoritmo encuentra el elemento mas grande con una direccion distinta de cero y lo intercambia en la direccion indicada 1 3 2Si esto hace que el elemento elegido alcance la primera o la ultima posicion dentro de la permutacion o si el siguiente elemento en la misma direccion es mayor que el elemento elegido la direccion del elemento elegido se establece en cero 3 1 2Despues de cada paso todos los elementos mayores que el elemento elegido que anteriormente tenia la direccion cero tienen sus direcciones establecidas para indicar el movimiento hacia el elemento elegido Es decir positivo para todos los elementos entre el inicio de la permutacion y el elemento elegido y negativo para los elementos hacia el final Por lo tanto en este ejemplo despues de que el numero 2 se mueve el numero 3 se vuelve a marcar con una direccion 3 2 1Los dos pasos restantes del algoritmo para n 3 son 2 3 1 2 1 3Cuando todos los numeros quedan sin marcar el algoritmo termina Este algoritmo toma tiempo O i para cada paso en el que el mayor numero para moverse es n i 1 Por lo tanto los intercambios que involucran el numero n toman solo tiempo constante Dado que estos intercambios representan todos menos una fraccion de 1 n de todos los intercambios realizados por el algoritmo el tiempo promedio por permutacion generada tambien es constante aunque un pequeno numero de permutaciones llevara una mayor cantidad de tiempo Una version sin bucle mas compleja del mismo procedimiento permite que se realice en tiempo constante por permutacion en todos los casos sin embargo las modificaciones necesarias para eliminar los bucles del procedimiento lo hacen mas lento en la practica 5 Interpretacion geometrica EditarEl conjunto de todas las permutaciones de n elementos puede representarse geometricamente mediante un permutoedro el politopo formado a partir del casco convexo de n vectores las permutaciones del vector 1 2 n Aunque se define en el espacio n dimensional en realidad es un politopo n 1 dimensional Por ejemplo el permutoedro en cuatro elementos es un poliedro tridimensional el octaedro truncado Si cada vertice del permutoedro esta marcado por la permutacion inversa a la permutacion definida por sus coordenadas de vertice el etiquetado resultante describe un grafico de Cayley del grupo simetrico de permutaciones en n elementos segun lo generado por las permutaciones que intercambian pares de elementos adyacentes Por lo tanto cada dos permutaciones consecutivas en la secuencia generada por el algoritmo Steinhaus Johnson Trotter corresponden de esta manera a dos vertices que forman los puntos finales de un borde en el permutoedro y toda la secuencia de permutaciones describe un camino hamiltoniano en el permutoedro un camino que pasa a traves de cada vertice exactamente una vez Si la secuencia de permutaciones se completa agregando una arista mas desde la ultima permutacion a la primera en la secuencia el resultado es un ciclo hamiltoniano Relacion con los codigos de Gray EditarUn codigo Gray para numeros en una raiz dada es una secuencia que contiene cada numero hasta un limite dado exactamente una vez de tal manera que cada par de numeros consecutivos difiere en uno en un solo digito El n las permutaciones de los n numeros del 1 al n se pueden colocar en correspondencia uno a uno con el n numeros del 0 al n 1 emparejando cada permutacion con la secuencia de numeros ci que cuentan el numero de posiciones en la permutacion que estan a la derecha del valor i y que contienen un valor menor que i es decir el numero de inversiones para el que i es el mayor de los dos valores invertidos y luego interpretar estas secuencias como numeros en el sistema de numeros factoriales es decir el sistema de radix mixto con secuencia de radix 1 2 3 4 Por ejemplo la permutacion 3 1 4 5 2 daria los valores c1 0 c2 0 c3 2 c4 1 y c5 1 La secuencia de estos valores 0 0 2 1 1 da el numero 0 0 0 1 2 2 1 3 1 4 34 Las permutaciones consecutivas en la secuencia generada por el algoritmo Steinhaus Johnson Trotter tienen un numero de inversiones que difieren en uno formando un codigo Gray para el sistema de numeros factoriales En terminos mas generales los investigadores de algoritmos combinatorios han establecido un codigo Gray para un conjunto de objetos combinatorios para que sea un orden de los objetos en los que cada dos objetos consecutivos difieren de la manera minima posible 6 El algoritmo en diferentes lenguajes de programacion EditarJAVA 7 public class JohnsonTrotter public static void perm int n int p new int n permutation int pi new int n inverse permutation int dir new int n direction 1 or 1 for int i 0 i lt n i dir i 1 p i i pi i i perm 0 p pi dir StdOut printf 0 1 n public static void perm int n int p int pi int dir base case print out permutation if n gt p length for int i 0 i lt p length i StdOut print p i return perm n 1 p pi dir for int i 0 i lt n 1 i swap StdOut printf d d n pi n pi n dir n int z p pi n dir n p pi n z p pi n dir n n pi z pi n pi n pi n dir n perm n 1 p pi dir dir n dir n public static void main String args int n Integer parseInt args 0 perm n C 8 include lt cstdlib gt using namespace std struct Arista unsigned o unsigned d int peso LAristas sig typedef LAristas Arista typedef TGrafo LArista N typedef TVector int N typedef TMatriz TVector N void johnson const TGrafo amp grafo int ig TMatriz amp distancias TMatriz amp previos Arista p TVector min caminos TVector aux dist TVector aux prev grafo ig nueva arista ig 1 0 NULL ig p grafo ig for unsigned i 2 i lt ig 2 i p gt sig nueva arista ig i 0 NULL p p gt sig BellmanFord grafo ig min caminos for unsigned i 1 i lt ig 1 i p grafo i while p NULL p gt peso p gt peso min caminos p gt o min caminos p gt d p p gt sig for unsigned i 1 i lt ig 2 i Dijkstra grafo i 1 aux dist aux prev previos i 1 aux prev CalcularDistancias grafo previos aux dist distancias PYTHON 9 def nobody while True yield False The term troll is taken from Knuth s choice of word def sjt pi inv i trolls d 1 Directoin 1 is descending 1 is ascending while True j inv i j is the position of the current troll if pi j lt pi j d d d yield next trolls i 1 else pi j pi j d pi j d pi j inv i d inv pi j d yield True def setup n Pad pi with n 2 so that pi i will always be lt the two ends pi n 2 i for i in range 1 n 1 n 2 inv pi 1 nobody simply continuously yields False By adding a nobody generator at both ends of trolls False is autmatically yieded by sjt when needed trolls nobody trolls extend sjt pi inv i 1 trolls for i in range n trolls nobody The lead troll will be the item n in the permutation lead troll trolls 2 return pi lead troll def permutations n pi lead troll setup n yield pi 1 1 while next lead troll yield pi 1 1 def cyclic test n pi lead troll setup n c 0 while True print Output join str x for x in pi 1 1 c 1 if not next lead troll print print c print sleep 1 c 0 if name main print n join join str x for x in pi for pi in permutations 1 print n join join str x for x in pi for pi in permutations 2 print n join join str x for x in pi for pi in permutations 3 print n join join str x for x in pi for pi in permutations 4 cyclic test 3 Vease tambien EditarAlgoritmo de Heap Algoritmo de Fisher YatesReferencias Editar Steinhaus Johnson Trotter algorithm Wikipedia en ingles fechaacceso requiere url ayuda McGuire Gary Bells motels and permutation Linguistica Johnson Trotter Algorithm in VC NET The Coders Lexicon www coderslexicon com Levitin Anany Introduccion al diseno de algoritmos Programacion Even Shimon Graph Algorithms Estudio de Algoritmos Savage Carla 1 de enero de 1997 A Survey of Combinatorial Gray Codes SIAM Review 39 4 605 629 ISSN 0036 1445 doi 10 1137 S0036144595295272 Consultado el 25 de abril de 2020 JohnsonTrotter java Algoritmo de Johnson Wikipedia la enciclopedia libre 20 de abril de 2020 Steinhaus Johnson Trotter SJT Permutation Generation Algorithm in Python using Coroutines Generators Gist en ingles Datos Q4925248 Obtenido de https es wikipedia org w index php title Algoritmo de Steinhaus Johnson Trotter amp oldid 132440921, wikipedia, wiki, leyendo, leer, libro, biblioteca,

español

, española, descargar, gratis, descargar gratis, mp3, video, mp4, 3gp, jpg, jpeg, gif, png, imagen, música, canción, película, libro, juego, juegos