¿Por qué no tomar la representación unaria de números en algoritmos numéricos?

15

Un algoritmo de tiempo pseudo-polinomial es un algoritmo que tiene tiempo de ejecución polinomial en el valor de entrada (magnitud) pero tiempo de ejecución exponencial en el tamaño de entrada (número de bits).

Por ejemplo, probar si un número n es primo o no, requiere un ciclo a través de los números del 2 al n1 y verificar si n mod i es cero o no. Si el mod tarda O (1) tiempo, la complejidad del tiempo general será O (n).

Pero si dejamos que sea ​​el número de bits necesarios para escribir la entrada, entonces x = log n (binario), entonces n = 2 x y el tiempo de ejecución del problema será O ( 2 x ), que es exponencial.xx=lognn=2x2x

Mi pregunta es, si consideramos la representación unaria de la entrada , entonces siempre x = ny luego el tiempo pseudo-polinomial será igual a la complejidad del tiempo polinomial. Entonces, ¿por qué nunca hacemos esto?nx=n

Además, dado que existe un algoritmo de tiempo pseudo-polinomial para la mochila, tomando , la mochila será polinómica como resultado P = NPx=n

M ama D
fuente
3
En realidad, hacemos esto, pero no con mucha frecuencia. Por las mismas razones, generalmente no tratamos con idiomas unarios, pero hay muchos resultados interesantes relacionados con estas bestias. ¿Lo has mirado?
André Souza Lemos
2
Sí, si elimina la diferencia entre tamaño y magnitud, pierde todos los conceptos que se basan en esa diferencia.
André Souza Lemos
77
Porque está poniendo al demonio en un lindo vestido. No hace nada más rápido, solo hace que la "complejidad del tiempo de ejecución" no tenga sentido.
Raphael
44
@Drupalist El problema de la mochila unaria en realidad no se conoce como NP completo porque la reducción normal al problema de la mochila supone que los números se escriben en binario. Si intenta hacer la reducción estándar pero escribe los números en unario, la reducción no se puede calcular en tiempo polinómico. Como resultado, el problema de la mochila unaria que se puede resolver en tiempo polinómico no significaría que P = NP.
templatetypedef
2
Es posible que desee consultar otras respuestas etiquetadas con pseudopolinomio , en particular esta .
Raphael

Respuestas:

17

Lo que esto significa es que la mochila unaria está en P. No significa que la mochila (con números codificados en binario) esté en P.

Se sabe que la mochila es NP-completa. Si mostraras que la mochila está en P, eso mostraría que P = NP.

Pero no ha demostrado que la mochila está en P. Ha demostrado que la mochila unaria está en P. Sin embargo, no se sabe que la mochila unaria sea NP-completa (de hecho, la sospecha estándar es que probablemente no sea NP-complete ) Por lo tanto, poner una mochila unaria en P no implica que P = NP.


Entonces, ¿qué problema debería importarnos más, la mochila o la mochila unaria? Si su motivación se basa en preocupaciones prácticas, entonces la respuesta dependerá del tamaño de los números para los que desea resolver el problema de la mochila: si son grandes, entonces ciertamente le importa más la mochila que la mochila unaria. Si su motivación se basa en preocupaciones teóricas, entonces la mochila es posiblemente más interesante, ya que nos permite obtener una comprensión más profunda, nos permite hacer una distinción entre tamaño y magnitud, mientras que la mochila unitaria nos impide hacer esa distinción.


Para responder la pregunta de seguimiento sobre el algoritmo de programación dinámica para el problema de la mochila:

Sí, el mismo algoritmo de programación dinámica se puede aplicar tanto a las mochilas como a las mochilas unarias. Su tiempo de ejecución es polinomial en la magnitud de los números, pero exponencial (no polinomial) en la longitud de los números cuando se codifica en binario. Por lo tanto, su tiempo de ejecución es polinómico en la longitud de la entrada cuando la entrada está codificada en unario, pero no es polinomial en la longitud de la entrada cuando la entrada está codificada en binario. Es por eso que hacemos consideran este algoritmo de programación dinámica para ser un algoritmo de tiempo polinómico para la mochila unario, pero no consideramos que sea un algoritmo de tiempo polinómico para la mochila (codificación binaria).

Recuerde que decimos que un algoritmo se ejecuta en tiempo polinómico si su tiempo de ejecución es como máximo algún polinomio de la longitud de la entrada, en bits .

DW
fuente
1
Muchas gracias, no sabía que la clase de complejidad de unario y no unario del mismo algoritmo puede ser diferente. ¿Por qué la solución de programación dinámica de la mochila estándar no se puede aplicar a la mochila unaria, y lleva a diferentes clases de complejidad? Tengo problemas para comprender la versión unaria de los problemas.
M ama D
@Drupalist, he editado mi respuesta para agregar dos párrafos al final para responder esa pregunta.
DW
Muchas gracias, por lo que entiendo, la diferencia entre el tamaño de entrada y su magnitud es la razón de la distinción entre polinomio y pseudo-polinomio, mediante el uso de representación unaria intenté eliminar esta diferencia, si olvidamos la mochila y volvemos a lo numérico algoritmos, me gustaría saber estableciendo ¿cuál será la interpretación de polinomio y pseudo-polinomio? Gracias de nuevox=n
M ama D
@Drupalist, no estoy completamente seguro de lo que quieres decir con , así que no estoy seguro de cómo responder. En este punto, sugeriría que sería mejor hacer una nueva pregunta (independiente) (y definir todas sus variables en esa pregunta). Esta plataforma no es tan buena para preguntas de seguimiento o de ida y vuelta: la mejor manera de manejarla es hacer una nueva pregunta, basada en lo que ha aprendido de las respuestas a esta pregunta. x=n
DW
1
@NikosM., OK, lo tengo. Gracias por la respuesta. Personalmente, no creo que esa declaración sea incorrecta, así que la dejaré como está. (Mi razonamiento: la longitud de la entrada depende de la elección de la representación, por lo que no creo que contradiga nada de lo que escribió). Sin embargo, es muy posible que mi perspectiva sea demasiado limitada, o que una explicación más detallada o una explicación de una perspectiva diferente podría agregar valor. Siéntase libre de escribir una respuesta adicional o sugerir una edición si cree que este punto podría ser más claro.
DW
6

Añadiría una pequeña cosa a la respuesta de DW:

He visto personas que piensan que debido a que la mochila unaria está en P, por lo tanto, podemos usarla en lugar de la mochila cuyos mejores algoritmos actuales tienen un tiempo exponencial.

Deje que la entrada sea y k y considerar el algoritmo de programación dinámica para la mochila y la mochila unario. El tiempo de ejecución para ambos es O ( n k ) . Es el mismo tiempo de ejecución. Es decir, si tiene una entrada, no importará si utiliza la programación dinámica para la mochila unaria o la programación dinámica para la mochila. Ambos tomarán (aproximadamente) la misma cantidad de tiempo para resolver la instancia del problema. Teóricamente, en cualquier lugar donde use uno, también puede usar el otro. Solo necesita convertir números de unario a binario y viceversa.W={w1,,wn}kO(nk)

O(nk)

Si le preocupa un problema de forma aislada, puede hacerlo. En realidad, eso es lo que a menudo hacen las personas en algoritmos. La complejidad de los algoritmos gráficos a menudo se expresa en términos de la cantidad de vértices y la cantidad de aristas, no del tamaño de la cadena que los codifica.

Pero esto es solo cuando estamos lidiando con un problema aislado. No es útil cuando se trata de problemas con diferentes tipos de entradas. Para los gráficos podemos hablar sobre el tiempo de ejecución wrt para el número de vértices y bordes. Para la mochila podemos hablar sobre la cantidad de artículos y el tamaño de la mochila. Pero, ¿y si queremos hablar de ambos? Por ejemplo, cuando queremos reducciones entre problemas, o discutir una clase de problemas que incluye problemas arbitrarios, no solo aquellos con un gráfico como entrada. Necesitamos un parámetro universal de entradas. Una entrada en general es solo una cadena, somos nosotros quienes interpretamos sus símbolos como números unarios, números binarios, gráficos, etc. Para desarrollar una teoría general de la complejidad del algoritmo y los problemas, necesitamos un parámetro general de las entradas. El tamaño de la entrada es una opción obvia y resulta ser lo suficientemente robusta como para que podamos construir una teoría razonable sobre ella. No es la única posibilidad. Para uno artificial podemos construir una teoría basada en2

k100100k21001kk21001

nnp(n)kp(n)k2p(n)1kk

nk

Kaveh
fuente
Muchas gracias, una pregunta más, al convertir la entrada a su representación unaria, ¿qué sucederá con el problema de determinar si un número es primo o no? Este problema es polinómico basado en la magnitud de entrada pero exponencial basado en bits de entrada (como señalé en la pregunta), ¿esta conversión hará algo mejor?
M ama D
@Drupalist, digamos que estamos usando el algoritmo simple que supera los números menores de nortehasta que encuentre un factor. Su tiempo de ejecución esO(norte) independiente de si codifica nortecomo unario o como binario. Si tiene un número de 1024 bits comosi=21024-1, el algoritmo va a tomar (aproximadamente) 21024-1 independiente de si das 21024-1como unario o como binario. Para una entrada particular en la que desea ejecutar su algoritmo, no cambia mucho si la da como unaria o binaria.
Kaveh
buena aclaración, sin embargo, eche un vistazo a mi comentario en la respuesta de DW que está relacionado con esta publicación
Nikos M.
2

En resumen y simple, te mostraré por qué.

Supongamos que tiene un algoritmo de factorización. Excepto por la pequeña diferencia de que uno acepta enteros para la entrada y el otroTunlly. Como puede ver, ambos fragmentos de código son similares.

x = input integer

factors = [];

for i in range(1, x + 1):
    if x % i == 0:
     factors.append(i)

 print(factors)

Observe que el algoritmo anterior es polinomial del valor numérico de X. TomaráXcantidad de pasos en el bucle. Pero cuando se trata del tamaño de bits, en realidadO(2norte).

Supongamos que hago una pequeña edición del código que tomará Tunlly/ /Unorteunry. Ahora seráO(norte) tiempo en valor y longitud de la entrada X.

x = input tallies

factors = [];

for i in range(1, x + 1):
    if x % i == 0:
     factors.append(i)

 print(factors)

La representación de entrada no hace que el código se ejecute más rápido. A pesar de que el segundo algoritmo es realmente poli-tiempo. No es muy práctico para encontrar los factores de RSA.

Travis Wells
fuente
Buen ejemplo, gracias
M ama D