Consultas, desarrollo de programas y petición de presupuestos:

jueves, 12 de julio de 2012

examen 2: solución del alumno

Utilizando estructuras definidas por el usuario.

main.h


typedef struct {
    char nombre[15];
    int intentos;
} puntuacion;

// declaracion de funciones
void reiniciarAleatorio();
void mostrarMenu();

void limpiarpantalla();

int pedirNum(char *);

void mostrarTablaDeRecord(puntuacion *);

void jugar(puntuacion *);

#define TAMANO 11

void AbrirFicheroOCrearlo(puntuacion *);
void SalvarFicheroDatos(puntuacion *);

void guardarTabla(int n,char *);


main.c

#include <stdio.h>
#include <stdlib.h>
#include <limits.h>
#include <time.h>
#include <string.h>
#include "main.h"


//entrada del programa
int main(int argc, char **argv)
{
// definir variables
    puntuacion TablaRecords[TAMANO]; //el la posicion t[10] se guarda el numero ultimo de intentos...
    int op=0;

//reiniciar el rnd
    reiniciarAleatorio();

//reinicio tabla de record o la leo de un archivo....
    while (op<TAMANO) {
        TablaRecords[op].intentos=INT_MAX;
        op++;
    }

    op=1;// para el menu

//leer el archivo de resultados del juego, y si no existe crearlo
    AbrirFicheroOCrearlo(TablaRecords);


    printf("***********************************************\n");
    printf("******** JUEGOS DE ACEPTAR LOS NUMEROS ********\n");
    printf("***********************************************\n");

// mostrar menu:
    while (op!=3) {
// mostrar menu:
//             1.mostrar tabla de record
//             2.jugar
//             3.fin del programa
        mostrarMenu();
        op=pedirNum("Indique la opción deseada:");
        switch(op) {
        case 1:
            mostrarTablaDeRecord(TablaRecords);
            break;
        case 2:
            jugar(TablaRecords);
            break;
        case 3:
            break;
        default:
            printf("Opción no valida\n");
        }
    }
    // guardo los datos de los record:
    SalvarFicheroDatos(TablaRecords);
    printf("Fin del juego, Adios....\n");




//**************jugar***********

//el programa elige un numero aleatorio

// mientras no acierte
//            escribe un numero el usuario
// ver si es menor ponerle mensaje. Numero de intentos ++
// ver si es mayor ponerle mensaje  Numero de intentos ++
// si es igual acerto, salida del bucle y guarda en la tabla el numero de intentos..
//



// guardar la tabla del numero de intentos
    /* Guardamos 10registros de record, + 1 PARA EL ULTIMO VALOR METIDO
     * comprobar que posicion esta (ordenar)
     * si esta fuera de la tabla no se guarda, si no se introduce numero
     * y si translada la posicion de los otros numeros.
     */

    return 0;
}


// ------------------------------------------------
// procedimientos y funciones
// ------------------------------------------------
void reiniciarAleatorio()
{
    srand(time(NULL));
}


// ------------------------------------------------
// menu
// ------------------------------------------------
//             1.mostrar tabla de record
//             2.jugar
//             3.fin del programa
void    mostrarMenu()
{
    limpiarpantalla();
    printf( "*********** Menu ****************\n");
    printf( "  1- Mostrar tabla de record\n");
    printf( "  2- Jugar\n");
    printf( "  3- Fin del programa\n");
    printf( "*********************************\n");

}

void limpiarpantalla()
{
    int c=0;
    for (c=0; c<5; c++) {
        printf("\n");
    }

}

// pedir numero para el menu..
// Pide un número entero por teclado. Muestra el texto indicado
int pedirNum(char *texto)
{
    char entrada_texto[10];
    char vaciabufferteclado[10];
    int num = 0;

    printf("%s", texto);
    num=atoi(gets(entrada_texto)); // convertimos cadena de texto en un numero int, con la funcion atoi
   // ver nota a pie de pagina del uso del gets.

    return num;
}

void mostrarTablaDeRecord(puntuacion *tabla)
{
    limpiarpantalla();
    char op2[5];
    int c=0;
    printf("***************** Tabla de Record ****************\n");
    printf("*  Posicion                 Record      Jugador  *\n");

    while (c<(TAMANO-1)) {
        //pongo TAMANO-1, porque solo quiero hacer que se muestren los 10 primeros.

        if (tabla[c].intentos!=2147483647) {
            printf("* %2dº ................. %7d          %5s      *\n",c+1,tabla[c].intentos,tabla[c].nombre);
            c++;
        } else {
            printf("* %2dº ................... no record      xxxxxx  *\n",c+1);
            c++;
        }
    }
    printf("***************** Tabla de Record ****************\n");

//    printf("Pulse S para salir  ");

}


// jugar devuelve el numero de repeticiones hechas por el jugador antes de resolver la solucion
void jugar(puntuacion *tabla)
{
    char cadena[20];
    int c;
    int pos;
    int op2;
    int indice;
    int solucion;
    int salir=1;
    int repeticiones=0;
    int numero=0;
    char nombre[15];
    char *texto;
    //pruebo con 10.... aunque deberia de ser 10000
    solucion=1+(int) (10.0*rand()/(RAND_MAX+1.0));

    printf("\n");
    printf("\n");
    printf("***********************************************\n");
    printf("*************** A JUGAR ***********************\n");
    printf("***********************************************\n");
    while (salir=1) {
        numero=pedirNum("Introduce un número:");
        if (numero==solucion) {
            break; // asi salgo del bucle...
        } else {
            if (numero>solucion) {
                printf("la solucion es MENOR... intentalo de nuevo\n");
                repeticiones++;
            } else {
                printf("la solucion es MAYOR... intentalo de nuevo\n");
                repeticiones++;
            }
        }

    }

    printf("\n Lo has hecho en %d intentos...\n",repeticiones);


    //     repeticiones;
    /* compruebo en la tabla de record, si las repeticiones las tengo que
     * introducir , si son nuevo record (o estar en la lista de 10 mejores), o no
     * */

    // determinar la posicion en la tabla....

    c=0;
    pos=0;
    while ((tabla[pos].intentos<repeticiones) && (pos<(TAMANO-1))) {
        pos++;

    }
    if (pos<TAMANO) {
        indice=TAMANO-1;
        while (indice>pos) {
            tabla[indice].intentos=tabla[indice-1].intentos;
            indice--;
        }
        tabla[pos].intentos=repeticiones;
        printf("Introduce el nombre del jugador (maximo 14 caracteres): ");
        texto=gets(nombre);

        strcpy(tabla[pos].nombre,texto);

        //guardarTabla(pos,texto); // pos es un int, y texto es un puntero
    }

}


// ---------------------- abrir o crear archivo de datos ----------------

void AbrirFicheroOCrearlo(puntuacion *tabla)
{
    int c=0;
    FILE *pf;
    if ((pf=fopen("/home/julio/records.txt","r"))==NULL) {
        // no puedo abrir el archivo, tengo que crearlo ...
        pf=fopen("/home/julio/records.txt","w");
        // me da problemas el ~/, me dice fallo de segmentacion...
        // tengo que poner /home/julio/records.txt

        fwrite(tabla,sizeof(puntuacion),TAMANO, pf);
        fclose(pf);

        // ya lo he creado
    } else {
        // leer datos de los puntos record

        fread(tabla,sizeof(puntuacion),TAMANO,pf);
        fclose(pf);
    }

}


void SalvarFicheroDatos(puntuacion *tabla)
{
    FILE *pf;
    int c=0;
    pf=fopen("/home/julio/records.txt","w");
    // me da problemas el ~/, me dice fallo de segmentacion...
    // tengo que poner /home/julio/records.txt


    fwrite(tabla,sizeof(puntuacion),TAMANO,pf);
    //}


    fclose(pf);
    // ya lo he creado
}


Nota al pe de pagina:
Cuando compilamos este ejercicio, nos da un aviso:
warning: the `gets' function is dangerous and should not be used.

Este aviso se debe a que gets, puede producir desbordamiento, ya que el usuario puede introducir mas caracteres que los que tengamos asignados a la variable de texto.

Para solucionar este problema lo suyo es utilizar la funcion fgets

No hay comentarios:

Publicar un comentario en la entrada