¿Existe un algoritmo que pueda combinar y separar números?

La respuesta fácil:

Si sus números tienen un mínimo de cero y un valor máximo de N, puede verlos como dígitos de un número base N + 1 y luego convertirlo a decimal.

public static int Pack (IEnumerable números, int max)
{
int retval = 0;
foreach (int número en números)
{
retval + = número;
retval * = max + 1;
}
retorno retval;
}

Para recuperar los números, conviértalo de nuevo a un número en base max + 1, y luego lea los dígitos.

public static IEnumerable Unpack (int número, int max)
{
while (número> 0)
{
número de retorno de rendimiento% (max + 1);
número / = max + 1;
}
}


Si sus números no tienen un valor máximo, entonces esto se vuelve mucho más complicado, pero aún se puede hacer. Consideremos solo dos números, A y B, que son cualquier cosa no negativa.

La idea es codificar A y B de la siguiente manera:

si
0 1 2 3 4
+ ———
0 | 0 2 5 9 14
1 | 1 4 8 13
A 2 | 3 7 12
3 | 6 11
4 | 10

Observe que las salidas están dispuestas en “capas” diagonales, por lo que no tenemos que lidiar con filas finitas. El “número de capa” es simplemente la suma de A y B. El primer valor en esta “capa” es el enésimo número triangular:

[matemáticas] inicio = \ frac {capa (capa + 1)} {2} [/ matemáticas]

A partir de aquí, podemos agregar B para obtener la respuesta final.

Paquete estático público int (int a, int b)
{
int suma = a + b;
int inicio = suma * (suma + 1) / 2;
retorno inicio + b;
}

Ahora hagamos tres números. Aquí, necesitamos un gráfico tridimensional, con “capas” bidimensionales. La idea es la misma, pero con una función diferente para obtener el número de inicio de la capa:

Paquete int estático público (int a, int b, int c)
{
int suma = a + b + c;
int inicio = suma * (suma + 1) * (suma + 2) / 6;
inicio de retorno + paquete (b, c);
}

Podemos trabajar la idea general en una función recursiva para N números;

public static int Pack (lista IEnumerable )
{
int cuenta = list.Count ();
si (cuenta == 0)
{
devuelve 0;
}
más
{
int sum = list.Sum ();
int inicio = 1;
para (int i = 0; i <cuenta; i ++)
{
inicio * = suma + i;
inicio / = i + 1;
}
return start + Pack (Cola (lista));
}
}

Sin embargo, deshacer esto es un oso. Para dos números, necesitamos recuperar en qué capa estamos encontrando la “raíz triangular” del número.

public static IEnumerable Unpack2 (int número)
{
// encuentra la “raíz triangular” del número.
int sum = (int) ((Math.Sqrt (1 + 8 * número) – 1) / 2);
int inicio = suma * (suma + 1) / 2;
int b = número – inicio;
int a = sum-b;
rendimiento de rendimiento a;
rendimiento de rendimiento b;
}

Hacer esto para el caso general es mucho más difícil, ya que requiere que encontremos el inverso de los números triangulares generalizados. Esto se deja como un ejercicio para el alumno.

public static IEnumerable Unpack (int number, int count)
{
si (cuenta == 0)
{
ruptura de rendimiento;
}
más
{
int sum = FindLayer (número, recuento); // ¡Buena suerte!
int inicio = 1;
para (int i = 0; i <cuenta; i ++)
{
inicio * = suma + i;
inicio / = i + 1;
}
int last = number = start;
foreach (int i en Unpack (número – último, cuenta – 1))
{
rendimiento de rendimiento i;
}
rendimiento de retorno último;
}

}

Se han dado las “respuestas fáciles”. Ahora presento el método ineficaz y absolutamente horrible que se me ocurrió hace un tiempo.

Recuerde que el número [math] \ pi [/ math] es irracional, ¡no solo eso, es trascendental!

Esto significa que, para cualquier conjunto de razones [matemáticas] r_i [/ ​​matemáticas], la ecuación [matemáticas] r_1 + r_2 \ pi + r_2 \ pi ^ 2 + r_3 \ pi ^ 3 + \ ldots + r_n \ pi ^ n = 0 [/ math] solo es verdadero si [math] r_i = 0 [/ math] para todos [math] i [/ math].

¡Podemos usar esto para nuestra ventaja! Digamos que me das una lista de [matemáticas] n [/ matemáticas] racionales [matemáticas] a_i [/ ​​matemáticas]. Ahora construimos nuestro número como antes, [math] C = a_1 + a_2 \ pi + \ ldots + a_n \ pi ^ n [/ math].

¿Cómo se puede dividir esto en sus componentes? ¡Fácil! Solo adivina hasta que lo hagas bien. Pero eso deja la pregunta, si tenemos UNA solución, ¿sabemos que es LA solución?

La respuesta es sí. Si tenemos [math] x_i [/ ​​math] y [math] y_i [/ ​​math] dos soluciones diferentes que dan la misma [math] C [/ math], tenemos que

[matemáticas] (x_1 – y_1) + (x_2 – y_2) \ pi + \ ldots + (x_n – y_n) \ pi ^ n = 0 [/ matemáticas]

¡Así, por la trascendentalidad de [matemáticas] \ pi [/ matemáticas], [matemáticas] x_i = y_i [/ ​​matemáticas] y de hecho son lo mismo!

Sin embargo, no hay una buena manera de ENCONTRAR la solución.

“¿Existe un algoritmo que pueda combinar y separar números?” El algoritmo dependería de lo que usted quiere decir con “número”. Pero puede hacerse. Tomando el ejemplo más simple, para dos enteros no negativos [matemática] a [/ matemática] y [matemática] b [/ matemática], forme el número [matemática] 2 ^ a * (2b + 1) [/ matemática]. Esto no solo conserva los dos números sino también su orden.

Suponiendo que los 5 números son reales, podemos crear un número de Octonion.

Cada número será un coeficiente diferente de una unidad de octonion diferente.

El número final se puede dividir fácilmente en los 5 números originales. Usando los Octonions, podemos combinar hasta 8 números reales diferentes para cumplir con sus restricciones.

¿Número único significa qué? ¿Es primo? Sí, creo que se puede hacer. Especialmente la teoría fundamental de la aritmética es útil para factorizar grandes números en sus factores primos. Estos son los fundamentos de la teoría de números. Estos son tan básicos que puede escribir sus propios algoritmos.

Puede interpretar la representación ASCII del texto [math] n_1, n_2, n_3, n_4, n_5 [/ math] como un número. Esa es la forma más práctica de hacerlo.

More Interesting

¿Cuál es la diferencia entre un algoritmo genético y un algoritmo de escalador?

Para el siguiente algoritmo sea n = 0. Para cada persona en la sala, establezca n = n + 1 '. ¿Dónde exactamente explica el algoritmo que compones n?

Cómo escribir una función recursiva usando Python que toma una cadena como entrada e imprime cada carácter en una línea separada

¿Cuál es la mejor manera de dominar los algoritmos de clasificación?

¿Cómo se puede probar que la ruta única a través de un árbol de expansión mínima entre dos nodos es una ruta más corta de "cuello de botella"?

¿Se puede demostrar que es imposible volver a un entero inicial mayor que uno si aplica un algoritmo de multiplicar por tres y agregar uno cuando es impar y dividir por dos si es par?

¿Cuáles son las principales diferencias, con ejemplos, entre un algoritmo de aprendizaje profundo y un algoritmo de aprendizaje de refuerzo?

¿Cuál es la diferencia entre las estructuras de datos de std :: vector y std :: deque?

¿Cuáles son algunas de las preguntas famosas al calcular los caminos más cortos (gráficos) usando Dijkstra's, DAG y Bellman-Ford?

¿Cómo funciona el algoritmo de búsqueda de ciclo de Floyd? ¿De qué manera mover la tortuga al comienzo de la lista vinculada, mientras se mantiene a la liebre en el lugar de reunión, seguido de mover un paso a la vez, hace que se encuentren en el punto de inicio del ciclo?

¿Hay alguna forma algorítmica de distinguir palabras multisilábicas de palabras de una sola sílaba en inglés?

¿Cómo puedo diseñar una función hash que elija aleatoriamente 16 bits de un número de 32 bits?

¿Cómo funciona el algoritmo de despacho de Uber?

¿Por qué SuperMemo no es tan fácil de usar como Anki?

¿Cuál es un buen algoritmo para priorizar mensajes DENTRO de su bandeja de entrada?