elhacker.net cabecera Bienvenido(a), Visitante. Por favor Ingresar o Registrarse
¿Perdiste tu email de activación?.

 

 


Tema destacado: Arreglado, de nuevo, el registro del warzone (wargame) de EHN


  Mostrar Mensajes
Páginas: 1 2 3 [4]
31  Programación / Programación C/C++ / Re: NUMEROS PRIMOS en: 7 Diciembre 2010, 06:39 am
Me parece mucho más adeuado la respuesta que dio do while sobre la raiz cuadrada, ya que ésta es el "punto de simetría" de los divisores de un número. Un número entero "a" es divisor de otro entero "n" sí y sólo sí a*b=n, dónde "b" también es divisor de "n". Si a<raiz(n) entonces b>raiz(n)... y viceversa, osea que si no hallamos divisores antes de la raíz del número, podemos asegurar que tampoco los hay después.

También te sugiero que te acuerdes de buscar hasta la raíz del número INCLUSIVE, de otro modo el programa señalaría como primo a los cuadrados perfectos de primos.

Y por último te sugeriría, ya que sólo quieres ver la primidad de un número determinado, que abandones la búsqueda si encuentras algún divisor, acuerdate que no quieres saber la cantidad total de divisores, sólo con 1 bastará..
32  Programación / Programación C/C++ / Re: Brute Force Iterativo en: 2 Mayo 2010, 16:18 pm
 Para concluir, diría que no se puede decir que un método gane al otro. Son herramientas, con sus respectivas ventajas y desventajas.
 Y quería destacar una cosa en la conclusión:
 Hay que aprender a usar la recursividad cuando hay que hacerlo. Hay muchos casos que este mecanismo (el de la recursividad) debe ser usado para plasmar cierta resolución del problema y muchas veces, si no se tiene práctica, uno no se da cuenta de como hacerlo
33  Programación / Programación C/C++ / Re: Brute Force Iterativo en: 1 Mayo 2010, 18:37 pm
Correctísimo lo que dices.
Te dejo en este caso el código del Brute Force recursivo y vas a ver que el planteamiento en ambos casos difiere muchísimo. En el iterativo es como ya lo expliqué anteriormente, y el recursivos es más como una anidación de "n" sentencias for. "n" es variable y por lo tanto esto es sólo posible gracias a la recursividad.

Código
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3.  
  4. void brute_force (char caracteres[], int cant, int pos, char *password)
  5.    {
  6.  
  7.        if (pos==-1)
  8.            {
  9.            printf ("%s\n", password);
  10.            return;
  11.            }
  12.        int i;
  13.        for (i=0;i<cant;i++)
  14.            {
  15.            password[pos]=caracteres[i];
  16.            brute_force (caracteres, cant, pos-1, password);
  17.            }
  18.        return;
  19.  
  20.    }
  21.  
  22. int main(int argc, char *argv[])
  23. {
  24.    char caracteres[256], *password;
  25.    int longitud, cantidad;
  26.    double tiempo;
  27.    time_t t1, t2;
  28.  
  29.    printf ("Ingrese los caracteres a usar: ");
  30.    scanf ("%s", caracteres);
  31.    cantidad = strlen(caracteres);
  32.  
  33.    printf ("Ingrese la longitud maxima de la contraseña: ");
  34.    scanf ("%i", &longitud);
  35.  
  36.    password = (char*) malloc (longitud*sizeof(char));
  37.  
  38.    time (&t1);
  39.        password[longitud]= '\0';
  40.    brute_force (caracteres, cantidad, longitud-1, password);
  41.    time (&t2);
  42.    tiempo = difftime (t2, t1);
  43.    printf ("\tTiempo: %7.2f\n\n", tiempo);
  44.    free (password);
  45.    system("PAUSE");
  46.    return 0;
  47. }

Hay veces en que no te das cuenta como resolver un problema y verdaderamente recursivamente puede ser resuelto.

Se destacan, además, muchos métodos de ordenamientos recursivos.

Hay veces en que conviene utilizarla y hay veces en las que un planteamiento se debe hacer en forma recursiva... Por eso conviene saber COMO y CUANDO implementarla, darse cuenta rápido.

Pero también hay abusos a ella, haciéndose cosas que se podrían tranquilamente y casi sin ningún cambio, iterativamente.
Pero como vemos, en este programa, si bien el recursivo y el iterativo "hacen" lo mismo; el problema está planteado de diferentes formas...
34  Programación / Programación C/C++ / Re: Principiante necesita ayuda :) en: 1 Mayo 2010, 05:02 am
Acá nadie te va a dar código como pan fresco, pero siempre una mano.

Dividi lo que tenes que ingresar, lo que le das de dato a la pc para que trabaje y lo que tenés que lograr con ello.

¿Seguro que copiaste bien el problema TAL Y CUAL te lo dieron? Porque así nomás se presta a ambigüedades....

Y un consejo (yo todavia voy a secundaria asi que no sé, pero se lo doy a mis alumnos): si un profe te da eso y tenés alguna duda o su enunciado se presta a alguna duda o ambigüedad: PREGUNTÁ.

Y si es un exámen o ejercicio que no te puede contestar. O si te toca el profe que siempre por hacerse el malo dice: "piensen" y ni se fija si dio un ejercicio ambiguo (porque los hay de esos): usá la lógica y hacé como te paresca pero dejá bien en claro como lo interpretaste vos...

Si eso es 1º año de la facu la paso de rabona xD
35  Programación / Programación C/C++ / Re: Brute Force Iterativo en: 1 Mayo 2010, 04:04 am

Resultando la próxima combinación: 2111

El bucle interior hace que cuando la primera cifra esté en 0 (último digito en nuestra lista de cifras a utilizar) la vuelve a 1 (al principio) y avanza una la siguiente cifra.

Osea que si está 0111 lo convertirá a 1211

A su vez ese bucle se fija si esta segunda cifra no estaba (en el momento de hacerla avanzar) en su última letra y si lo fuese avanza la tercer.

Osea que si está en 0011 lo convertirá a 1121



¿Más o menos como un humano obtendría todas las combinaciones no?

Claro que detrás de esto, cuando se plasma el algoritmo pensado a código se usan recursos adicionales, como un vector de largo "longitud de password"+1 para que vaya indicando en que posición de la lista de los caracteres que combinaremos, está ubicado cada caracter de nuestra contraseña. (Se entiende mejor leyendo el código).
Así si nuestra lista es: "12ab"
Y nuestra contraseña es de 3 dígitos

Cuando el programa (entre todas las combinaciones que muestre) imprima: 1ba
Los números del vector explicado serán (en este orden) 0 3 2 (ya que el 1, es la letra
  • de "12ab", b es la letra [3] y a la letra [2] )

No es inútil este vector adicional, como verán ya que no siempre tendrán listas de caracteres a usar (o listas "fuentes" como me gusta llamarles) que son continuas en la tabla ASCII. Porque de ser así (de ser una lista continua como "abcdefg") no usaría el vector numérico del que hablaba y iría sumando +1 para hacer que la "a" se convierta en "b", la "b" en "c", etc hasta "g".
Pero en listas como "12ab" si sumo +1 a '2' obtengo '3' y no 'a'

¡Espero que se haya entendido! (cualquier cosa, está el código,pero no comentado)




Y para Littlehorse que me pidió  las mediciones aquí están:

Caracteres usado: "1234567890" (osea 10).
Longitud de password: 7.
Osea un total de 10^7 combinaciones, diez millones. Me pareció un número razonable. Ni muy mucho (porque cerré casi todo para hacer el test y no quería pasar mucho tiempo despegado de la pc xD), ni muy poco (porque si es poco pequeñas fluctuaciónes en la velocidad del procesador, procesos que activan, etc; influyen en mayor medida)
Resultados:

Iterativo:432
Recusivo:593
Diferencia: 2 min 41 segundos
Por eso sigo defendiendo A MUERTE la iteración! xD
36  Programación / Programación C/C++ / Re: Mastermind en: 1 Mayo 2010, 04:01 am
Bueno, ante la falta de comentarios creo que no entendieron de que va el juego.
Como no quiero privarlos de tal placer intelectual (sarcasmo).
Y quiero que comenten (verdadera intención).
He aquí un historial mío con los pensamientos deductivos que hice para adivinar el número a partir de las pistas. Vaya que tuve suerte, y me tocó un número fácil.
Capaz que tengo algún error de lógica porque mientras iba jugando una partida del juego anotaba mis deducciones y así como me quedo lo intercalé con el historial y lo pongo aquí.


Código:
---------------------------------------------------------
1233
Blancas: 0 Rojas: 0

...entonces no hay ni 1, ni 2 ni 3...


--------------------------------------------------------
4566
Blancas: 0 Rojas: 2

Hay un para rojo, puede ser:
4/5 5/6
4/6 6/6


------------------------------------------------------
6612
Blancas: 1 Rojas: 0

Con esto averigué que había un sólo 6 y que estaba en las posiciones 1 o 2
Por lo tanto el otro incorrecto debía ser un 4 o un 5 que podría ir en las posiciones 3 o 4 (para ambos) o 1 para el 5, o 2 para
el 4



------------------------------------------------------
6155
Blancas: 1 Rojas: 1

Esto puede significar que:
A) El 6 esté bien posicionado y que el 5 no va ni en 3, ni en 4, osea va en 2
B) O que el 6 vaya en 2 y el 5 esté bien en alguna de esas dos posiciones

Pero de cualquier modo nos asegura que el 5 está y por lo tanto el 4 queda descartado. Y que no hay más de un 5

***IMPORTANTE(vease abajo)

------------------------------------------------------
1651
Blancas: 2 Rojas: 0

Ahi me doy cuenta de que de las opciones A y B, la B es la correcta y además que el 5 va en la posicion 3.
Posibles (para las cifras sin adivinar): 7890



------------------------------------------------------
7891
Blancas: 1 Rojas: 0

Ahi sé que está bien el 7 y que ni el 8 ni el 9 están en el número, por lo que el dígito incógnita de la posición 4 es 0.



------------------------------------------------------
7650
Blancas: 4 Rojas: 0

Gané, me muestra el cartel que dice felicitaciones, que ustedes no verán nunca si no juegan! xD


***IMPORTANTE: no quiero hacer lío, pero soy un boludo importante. Cometí un error (igual gané, pero con un movimiento
 inecesario). La opción A es inválida: ya que si el 6 está bien en la pos 1, el 5 tiene que estar en la 2. Pero como vimos
antes el 5 no puede estar en 2! Por lo que logicamente el incorrecto es el 6... :P
37  Programación / Programación C/C++ / Brute Force Iterativo en: 30 Abril 2010, 05:43 am
Esto va para principalmente para Littlehorse, que me había pedido (hace mucho mucho mucho tiempo, quizás ni se acuerde) un brute force iterativo (yo había posteado uno recursivo).

Y aquí va:

Código
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4.  
  5. int main(int argc, char *argv[])
  6. {
  7.  int contadores[50], len, cant, i;
  8.  char caracteres[200], pass[50];
  9.  
  10.  printf ("Ingrese los caracteres a usar para la contrasena: ");
  11.  scanf ("%s", caracteres);
  12.  
  13.  printf ("Ingrese la longitud de la contraseña: ");
  14.  scanf ("%i", &len);
  15.  
  16.  cant = strlen (caracteres);
  17.  
  18.  /*contadores = (int *) malloc (sizeof (int) * (len+1) );
  19.   pass = (char *) malloc (len+1);*/
  20.  
  21.  for (i=0 ; i<len ; i++)
  22.    {
  23.        pass[i] = caracteres[0];
  24.        contadores[i] = 0;
  25.    }
  26.  contadores[i] = 0;
  27.  pass [i] = '\0';
  28.    //Inicio bucle
  29.  
  30.    while (!contadores[len])
  31.    {
  32.        printf ("%s\n", pass);
  33.  
  34.        for (i=0;contadores[i]==cant-1;i++)
  35.            pass[i] = caracteres [contadores[i] = 0];
  36.  
  37.        pass[i] = caracteres [++contadores[i]];
  38.    }
  39.  
  40.  /*free (contadores);
  41.   free (pass);*/
  42.  
  43.  system("PAUSE");
  44.  return 0;
  45. }
38  Programación / Programación C/C++ / Mastermind en: 30 Abril 2010, 05:31 am
Bueno, luego de un gran descanso empezaré a postear nuevamente mis cosillas.

Aquí un jueguito que muchos quizás lo tengan en su casa con el nombre de "Mastermind"

El juego se base en adivinar un número de n dígitos elegido aleatoriamente por la máquina (el número de dígitos n es ingreso).

Pero se cuentan con una serie de pistas, lo que no indica que en el juego no influya la suerte obvio, pero lo hace un juego más para pensar que para "tirar números al azar".

Estas pistas consiste en dar al usuario el número de cifras en las que ha acertado. Y el número de cambios o conmutaciones que podrían hacer para hacer que una ficha que está incorrecta, lo esté.
Un ejemplo vale más que mil palabras:

Imaginemos que n vale 4 (osea, estamos operando con 4 dígitos)

El número elegido por la pc es: 3345

Nosotros ingresamos el: 5542

Cantidad de aciertos (o blancas): 1 (el 4 en la tercera posición)
Cantidad de rojas: 1 (ya que si bien tengo dos 5, osea, dos incorrectas, en la incógnita tengo sólo un 5. Así que el otro está de más)


Código
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4. #define LIMPIAR_PANTALLA system("cls");
  5.  
  6.  
  7.  
  8.  
  9. int esnumero (const char usuario[], int cant)
  10.    {
  11.        while (cant)
  12.            if ( usuario[--cant]<'0' || usuario[cant]>'9' )
  13.                return 1;
  14.        return 0;
  15.    }
  16.  
  17.  
  18. int main(int argc, char *argv[])
  19. {
  20.  FILE *historial;
  21.  char *incognita, *usuario, h;
  22.  int cant, i, j, blancas, rojas;
  23.  srand (time(NULL));
  24.  
  25.  do {
  26.        printf ("Ingrese la cantidad de caracteres para jugar: ");
  27.        scanf ("%i", &cant);
  28.    } while (cant<1);
  29.  
  30.  do {
  31.      printf ("\n\nDesea guardar el historial de la partida (ingrese 1 por si y 0 por no): ");
  32.      scanf ("%i", &h);
  33.    } while (h!=0&&h!=1);
  34.  
  35.  if (h)
  36.    if (! (  historial = fopen ("historial.txt", "w")  )  )
  37.        {
  38.            do {
  39.                printf ("\n\n\nHa surgido un error al crear el historial. Que desea hacer:\n1-Cerrar el programa\n2-Continuar sin guardar el historial\n\n\tOpcion: ");
  40.                scanf ("%i", &h);
  41.                } while (h!=0&&h!=1);
  42.            if (h)
  43.                return 0;
  44.            else
  45.                h=0;
  46.        }
  47.  
  48.  usuario = (char *) malloc (cant);
  49.  incognita = (char *) malloc (cant);
  50.  
  51.  for (i=0 ; i<cant ; i++)
  52.    incognita[i] = rand ()%10+'0';
  53.  incognita[cant] = '\0';
  54.  
  55.  if (h)
  56.    fprintf (historial, "%s\n\n\n", incognita);
  57.  
  58.  for (i=0,j=0 ; i<cant ; i++)
  59.    {
  60.    j *= 10;
  61.    j += 9;
  62.    }
  63.  // Programa propiamente dicho:
  64.  LIMPIAR_PANTALLA
  65.  printf ("A continuacion debe numeros entre 0 y %i hasta que adivine el numero\nLuego de cada numero le aparecera las pistas\n\nAprete una teclea para comenzar a jugar...", j);
  66.  system ("PAUSE>>nul");
  67.  LIMPIAR_PANTALLA
  68.  
  69.  do {
  70.        do
  71.            scanf ("%s", usuario);
  72.              while (strlen (usuario) != cant || esnumero (usuario, cant) );
  73.  
  74.        if (h)
  75.            fwrite (usuario, 1, cant, historial);
  76.  
  77.        blancas=0;
  78.        rojas=0;
  79.  
  80.        for (i=0;i<cant;i++)
  81.            if (incognita[i]==usuario[i])
  82.                {
  83.                    usuario[i] = 'b';
  84.                    blancas++;
  85.                }
  86.  
  87.        for (i=0;i<cant;i++)
  88.            if (usuario[i]!='b')
  89.                for (j=0;j<cant;j++)
  90.                    if (usuario[j]!='b'&&usuario[j]!='r'&&incognita[i]==usuario[j])
  91.                        {
  92.                        usuario[j] = 'r';
  93.                        rojas++;
  94.                        break;
  95.                        }
  96.  
  97.        if (h)
  98.            fprintf (historial, "\nBlancas: %i Rojas: %i\n\n", blancas, rojas);
  99.  
  100.        printf ("Blancas: %i Rojas: %i\n\n", blancas, rojas);
  101.  
  102.    } while (blancas!=cant);
  103.  
  104.    LIMPIAR_PANTALLA
  105.  
  106.    printf ("\n\tFELICITACIONES!\n\n\nUsted ha adivinado el numero (%s)\n\n", incognita);
  107.  
  108.  free (usuario);
  109.  free (incognita);
  110.  system("PAUSE");
  111.  return 0;
  112. }

Bueno, es un juego muy popular también en mi escuela.

PD: También posee la opción de guardar el historial del juego
39  Comunicaciones / Mensajería / Re: Recuperar cuenta hotmail en: 6 Diciembre 2009, 16:51 pm
auto hackeate con el bifrost y fijate las contraseñas guradas xD
Páginas: 1 2 3 [4]
WAP2 - Aviso Legal - Powered by SMF 1.1.21 | SMF © 2006-2008, Simple Machines