2010-07-28 20 views
5

Mi hermanito de 15 años está comenzando a programar, y él escribió un pequeño y prolijo programa que genera todas las combinaciones de letras y números de seis dígitos o menos. Su código era un bucle sextuple-anidado para actualizar los elementos de una matriz de caracteres de seis niveles. Se veía mal, ¡pero sin duda fue rápido! Le mostré cómo hacer un conteo simple, y convertir esos números a la base 36.¿Cómo puedo contar con una base numérica diferente en C++?

El mayor problema es que mi código era mucho más lento que el suyo, debido a la división que estaba haciendo. ¿Hay alguna forma de que simplemente pueda asumir la base 36 y dar salida a un conteo de 1 a 36^6?

Lo ideal es que estoy buscando hacer algo como

[base 36] 
for(int i = 0; i < 1000000; i++) 
    SaveForLaterFileOutput(i); 
+6

Usted confunde el valor con la presentación. El conteo puro no es un concepto al que se le puede dar una raíz. ¡Una versión refactorizada de la solución de tu hermano podría ser la mejor de las dos! –

+0

No hay una construcción basada en base36 en el lenguaje. Sin embargo, no necesitas división para hacer lo que quieras. – driis

Respuesta

3

Prueba esto:

char buffer[1024]; 
for(int i = 0; i < 1000000; i++) 
     cout << itoa (i, buffer, 36); 

Aquí es sin itoa (si no lo tiene)

cout << setbase (36); 
for(int i = 0; i < 1000000; i++) 
     cout << i << endl; 
cout << setbase (10); // if you intend to keep using cout 

+2

'itoa' no está en el estándar y no todas las bibliotecas de C++ lo incluyen. –

+0

Eso seguro hace este truco. Gracias. – Jeffrey

+0

Actualizado para tener una respuesta sin itoa (gracias @Konrad Rudolph) –

1

para convertir un número de base 36: hacer un acumulador y comenzar a partir de un grado suficientemente alto, por ejemplo 36^6. Si el acumulador más ese número es menor que su número, agréguelo al acumulador y repita para el mismo grado (el recuento de este es el valor del dígito), si es mayor, deséchelo. Repita para grados más bajos hasta llegar a 36^0. Lleve un registro del recuento de cada grado, y ese es su número en la base 36.

para imprimir de una manera significativa, hacer otra cosa.

1

Todos los números utilizados en los cálculos están en la base 2 Cualquier otro número que veas es solo una ilusión sobre cómo se imprime. Por lo tanto, su SaveForLaterOutput no tiene sentido.

La función de biblioteca itoa() (que se traduce como "entero en ASCII") (actualmente ha sido reemplazada por la función de seguridad _itoa_s()) le permite especificar la base cuando se prepara para la salida.

+0

No existe tal cosa como "2" en binario, por lo que, técnicamente, todos los cálculos están en base 10 binarios (no debe confundirse con el número diez que tanto nos gusta a los humanos). – fredoverflow

+0

Hay solo 10 tipos de personas en el mundo: los que entienden los binarios y los que no. –

+0

Hay 10 tipos de personas: los que entienden ternario, los que no y los que lo confunden con el binario;) –

2

Es posible que su hermano actualice su matriz de 6 elementos sin necesitar 6 bucles anidados. Mediante la modificación de la función increment continuación, puede contar en cualquier "base" a elegir:

#include <algorithm> 
#include <iostream> 

#define NUM_CHARS 6 

// assuming ASCII 
// advances through a chosen sequence 0 .. 9, a .. z 
// or returns -1 on overflow 
char increment(char &c) { 
    if (c == 'z') return -1; 
    if (c == '9') { c = 'a'; return c; } 
    return ++c; 
} 

int main() { 
    char source[NUM_CHARS+1] = {0}; 
    std::fill_n(&source[0], NUM_CHARS, '0'); 
    while (true) { 
     std::cout << source << "\n"; 
     int idx = NUM_CHARS; 
     // increment and test for overflow 
     while (increment(source[--idx]) == -1) { 
      // overflow occurred: carry the 1 
      source[idx] = '0'; 
      if (idx == 0) return 0; 
     } 
    } 
} 

no me he molestado con la "o menos" parte del problema: no obstante lo has hecho con 6 bucles probablemente también funcione con esta técnica. Estrictamente hablando, esto es enumerar combinaciones, que es casi, pero no exactamente lo mismo que contar.

Cuestiones relacionadas