Ejemplos de algoritmos recursivos sofisticados


14

Estaba explicando el famoso algoritmo determinista de selección de tiempo lineal ( algoritmo de mediana de medianas) a un amigo.

La recurrencia en este algoritmo (aunque es muy simple) es bastante sofisticada. Hay dos llamadas recursivas, cada una con diferentes parámetros.

Estaba tratando de encontrar otros ejemplos de algoritmos recursivos tan interesantes, pero no pude encontrar ninguno. Todos los algoritmos recursivos que se me ocurren son simples recursiones de cola o simples divide y vencerás (donde las dos llamadas son "iguales").

¿Puedes dar algunos ejemplos de recurrencia sofisticada?


Atravesar un laberinto o, más generalmente, un gráfico con una búsqueda de amplitud es un ejemplo simple de una recursión interesante.

Sin embargo, creo que BFS no califica para mi pregunta, ya que puede implementarse fácil y naturalmente usando una cola y un ciclo while.
elektronaj

¿Qué pasa con retroceder en la resolución de acertijos y análisis? Y los algoritmos de clasificación y clasificación también tienen recursiones no estándar.
uli

Algoritmos de memorización ?
Kaveh

2
@vzn: una cola no puede reemplazar una pila. BFS es un caso especial.
Raphael

Respuestas:


15

Mi recurrencia favorita aparece en algoritmos sensibles a la salida para calcular cascos convexos, primero por Kirkpatrick y Seidel , pero luego por otros. Deje denotar el tiempo para calcular el casco convexo de n puntos en el plano, cuando el casco convexo tiene h vértices. (El valor de h no se conoce de antemano, aparte del límite trivial h n .) El algoritmo de Kirkpatrick y Seidel produce la recurrencia T ( n , h ) = n 3  o  h T(norte,h)nortehhhnorte donden1,n23n/4yn1+n2=nyh1

T(norte,h)={O(norte)Si norte3 o h3T(norte1,h1)+T(norte2,h2)+O(norte)de otra manera
norte1,norte23norte/ /4 4norte1+norte2=norte .h1+h2=h

La solución es . Esto es un poco sorprendente, ya que h no es el parámetro que se divide de manera uniforme. Pero, de hecho, el peor caso de la recurrencia ocurre cuando h 1 y h 2 son ambos acerca de h / 2 ; si de alguna manera mágicamente h 1 es siempre constante, la solución sería T ( n , h ) = O ( n ) .T(norte,h)=O(norteIniciar sesiónh)hh1h2h/ /2h1T(norte,h)=O(norte)

Utilicé una variante de esta recurrencia en uno de mis primeros trabajos de topología computacional : donde n 1 + n

T(n,g)={O(n)if n3 or g=0T(n1,g1)+T(n2,g2)+O(min{n1,n2})otherwise
y g 1 + g 2 = g . Nuevamente, la solución es O ( n log g ) , y elpeor de loscasos ocurre cuando ambos nn1+n2=nsol1+sol2=solO(norteIniciar sesiónsol)norte como se dividen siempre de manera uniforme.sol

Tengo problemas con la condición "if or h = O ( 1 ) "; ¿Qué quiere decir O aquí? ¿Existen constantes globalmente limitantes que n y h tienen que socavarse para terminar en el caso uno (y los autores no se molestan en darlas). Porque si lo leo literalmente (es decir, interpreto tanto O ( 1 ) de la misma manera que O ( nnorte=O(1)h=O(1)OnortehO(1) en la misma fila) el caso dos nunca o siempre sucede (ni siquiera estoy seguro). Abuso de notación llevado demasiado lejos, en mi humilde opinión. O(norte)
Rafael

1
Lo siento, he editado mi respuesta para aclarar. significaba "tu constante favorita". ¡He usado 3 en mi revisión, pero 10 10 100 ! habría funcionado igual de bien. O(1)31010100!
JeffE

¿Cómo dibujó esos diagramas en los documentos de topología computacional?
user119264

12

La recursión que usé en mi artículo "Un algoritmo de tiempo lineal para calcular el diagrama de Voronoi de un polígono convexo" de Aggarwal et al también es bastante complicada.

Aquí hay una descripción del algoritmo de nuestro artículo. En caso de que no esté claro en la descripción, en el paso 3 los puntos rojos se dividen en puntos carmesí y granate. Los pasos 1, 3 y 6 son todos de tiempo lineal. También sabemos que si es el número total de puntos, | B | α n , | R | β n , y | C | γ n para algunos α , β , γ > 0 .norteEl |siEl |αnorteEl |REl |βnorteEl |CEl |γnorteα,β,γ>0 0

Te dejaré descubrir por qué todo el algoritmo toma tiempo lineal.

  1. Divide los puntos originales en los conjuntos azul y rojo B y R.
  2. Calcule recursivamente el casco convexo de los puntos azules.
  3. Usando la estructura del casco azul, seleccione los puntos carmesí C.
  4. Agregue los puntos carmesí al casco azul uno a la vez.
  5. Calcule recursivamente el casco convexo de los puntos de granate G.
  6. Combina este casco de granate con el casco azul expandido del paso 4.

Lo que hace que el algoritmo sea lineal es la capacidad de agregar una fracción fija de los puntos rojos al casco azul a un costo constante por punto. Los puntos agregados son los puntos carmesí.

T(norte)=T(El |siEl |)+T(El |solEl |)+O(norte)
El |siEl |El |solEl |El |siEl |+El |solEl |(1-γ)norte

7

Existe una variación en la mediana de recurrencia de hallazgos que proviene de la búsqueda de rango con medios planos. La recurrencia misma es de la forma

T(norte)=T(norte/ /2)+T(norte/ /4 4)+Cnorte
que es similar a la recurrencia de búsqueda media. Para obtener más información al respecto, consulte las notas de clase de Jeff Erickson y, en particular, la Sección 4.

1
Mi respuesta aquí ( cs.stackexchange.com/questions/332/… ) tiene exactamente la misma recurrencia para su tiempo de ejecución :)
Alex ten Brink

6

Hay un montón de algoritmos recursivos geniales [1], [2] utilizados en la predicción de la estructura secundaria de ARN. Dejado a sus propios dispositivos, una cadena de ARN formará pares de bases consigo mismo; un ejemplo relativamente simple de [3] calcula el número máximo de bases anidadas y emparejadas que se formará una cadena de ARN consigo misma:

METRO(yo,j)=metrounXyok<j-Lmetroyonorte{METRO(yo,k-1)+METRO(k+1,j-1)+1METRO(yo,j-1)


  1. Plegado óptimo por computadora de grandes secuencias de ARN utilizando termodinámica e información auxiliar por M. Zuker, P. Stiegler (1981)

  2. Algoritmo de programación dinámica para la predicción de la estructura de ARN que incluye pseudonudos por E. Rivas, SR Eddy (1999)

  3. Algoritmo rápido para predecir la estructura secundaria del ARN monocatenario por R. Nussinov, AB Jacobson (1980)


Uno relacionado propuesto aquí es bastante complejo, ya que presenta tres recursiones mutuamente dependientes (programación dinámica).
Raphael

4

Todavía no entiendo lo que quieres decir con "recursión sofisticada". Por ejemplo, el paso de recursión en el algoritmo FFT es sofisticado.

Pero si desea buscar una recursión más complicada , entonces la recursividad mutua podría ser una posible respuesta. La recursividad mutua es útil cuando se trabaja con lenguajes de programación funcionales . La recursividad mutua es la característica clave de los analizadores de descenso recursivo .


Bueno, la recurrencia en FFT (la forma más simple de Cooley-Tukey) es "estándar" divide y vencerás. Esto es evidente por su complejidad O (nlogn). Las 2 llamadas recursivas (1 para el par, 1 para las probabilidades) son algo "iguales".
elektronaj

3

Fuera de mi cabeza, la función McCarthy 91

F(N) = 
    n - 100    if n > 100
    F(F(n+11)) if n <= 100

y la función de Ackermann

A(m, n) = 
    n + 1             if m = 0
    A(m-1, 1)         if m > 0 and n = 0
    A(m-1, A(m, n-1)) if m > 0 and n > 0

podría contar como funciones recursivas poco convencionales, aunque juguetonas.

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.