void Juego::eventos() { switch (e) { case SALIR: break; case JUEGO: if (oponentes->numEnem() == 0) { cambiaEstado(FINFASE); } break; case MENU: if (bjugar != NULL) { if (bjugar->encima(Mx, My) && BRizq) { cambiaEstado(JUEGO); } } if (bsalir != NULL) { if (bsalir->encima(Mx, My) && BRizq) { cambiaEstado(SALIR); } } break; case SUBMENU: if (bSI != NULL) { if (bSI->encima(Mx, My) && BRizq) { cambiaEstado(MENU); } } if (bNO != NULL) { if (bNO->encima(Mx, My) && BRizq) { cambiaEstado(JUEGO); } } break; case GAMEOVER: if (BRizq) { cambiaEstado(MENU); } break; case FINFASE: if (BRizq) { if (mapas.esVacia()) { cambiaEstado(MENU); } else { fondo = IMG_Load(mapas.consulta().c_str()); cambiaEstado(JUEGO); } } break; } colisiones(); movimiento(); }
//funcion que se encarga de llamar a todas las funciones para poder jugar void partida(){ char matriz[FILAS][COLUMNAS], info[FILAS][COLUMNAS]; char respuesta, opcion, respuesta_anterior; int vidas, pos_usuario[USUARIO], pos_maquina[ENEMIGOS][2], nivel, puntuacion, cocos_anterior, asteriscos, turnos; bool asterisco_comido; /*---------------------------------------------------------------------------------------------*/ /*Englobar en una funcion*/ do{ //iniciamos la partida char dibujo_enemigo[ENEMIGOS] = {'M', 'M', 'M', 'M'}; asteriscos = 4; asterisco_comido = false; turnos = 0; vidas = 3; respuesta = 'j'; respuesta_anterior = 'a'; nivel = 1; puntuacion = 0; cocos_anterior = MCOCOS; cargar_mapa(matriz, info); inicializar_matriz(matriz, pos_usuario, pos_maquina, info, dibujo_enemigo); refrescar(matriz, info, vidas, nivel, puntuacion); while(respuesta != 'q' && vidas > 0){ respuesta = movimiento(respuesta_anterior); respuesta_anterior = respuesta; mover_jugador(respuesta, info, pos_usuario, matriz); comprobar_asteriscos(&asteriscos, info, dibujo_enemigo, &turnos, &asterisco_comido); comprobacion(matriz, info, pos_usuario, pos_maquina, vidas, nivel, puntuacion, dibujo_enemigo, asterisco_comido, &vidas); recuento_puntuacion(info, &cocos_anterior, &puntuacion); mover_maquina(matriz, pos_maquina, pos_usuario, dibujo_enemigo, asterisco_comido); comprobacion(matriz, info, pos_usuario, pos_maquina, vidas, nivel, puntuacion, dibujo_enemigo, asterisco_comido, &vidas); /*----------------------------------------------------------------*/ /*Ponerlo como funcion*/ if(comprobar_fin_nivel(info) == 1){ cargar_mapa(matriz, info); inicializar_matriz(matriz, pos_usuario, pos_maquina, info, dibujo_enemigo); nivel ++; cocos_anterior = MCOCOS; asterisco_comido = false; turnos = 0; asteriscos = 4; } /*---------------------------------------------------------------*/ refrescar(matriz, info, vidas, nivel, puntuacion); if(turnos > 0 ) turnos --; else{ for(int i=0; i<ENEMIGOS; i++) dibujo_enemigo[i] = 'M'; asterisco_comido = false; } } if(vidas == 0){ guardar_puntuacion(puntuacion); printw("\n\t\t\tGame Over\n"); } printw("¿Quieres jugar de nuevo? s/n\n"); refresh(); scanf(" %c", &opcion); }while(opcion != 'n'); /*--------------------------------------------------------------------------------------------------------*/ //exit (EXIT_SUCCESS); }//fin partida
int main() { short numevento = 0, mapactual, numlink, numitems = 0, mov, bat; char **map; bool updatemap = true; // Usado para determinar cuándo hay que refrescar la pantalla. bool update = false; // Usado para determinar cuándo hay que buscar una batalla. STRUCTpos VISION, tamMapa = { 0 }; STRUCTgraph graph; STRUCTcontroles controles; STRUCTpersonaje personaje; STRUCTeventos *evento; STRUCTitem *items; STRUCTlink *puertas; srand(time(0)); setlocale(LC_CTYPE, "Spanish"); mapactual = 0; // Mapa a cargar por defecto. inicializacion(&numitems, &VISION, &graph, &controles, &personaje, &items, &mapactual); //Inicialización de variables. intromenu(&items, controles, &personaje, &mapactual); // Menú de introducción (Nuevo juego, Cargar partida...). lectura(&numevento, &mapactual, &numlink, &tamMapa, &map, &evento, &puertas); // Primera lectura del mapa. do // Bucle principal. { bat = rand() % 25; if (bat == 0 && update == true) { batalla(numitems, controles, &personaje, items); updatemap = true; } if (updatemap == true) display(evento, VISION, tamMapa, graph, &personaje, map, numevento, mapactual); mov = movimiento(numevento, map, &controles, &personaje, evento); switch (mov) // El valor devuelto por la función movimiento determina si el personaje se ha movido a un terreno normal, a una puerta o se ha pulsado el menú. { case 1: // El personaje se ha movido a una puerta. if ((busquedaPuerta(&mapactual, &numlink, &personaje, puertas)) == 1) // Se busca la puerta de enlace y se asigna como actual el mapa de destino. { free(evento); updatemap = true; lectura(&numevento, &mapactual, &numlink, &tamMapa, &map, &evento, &puertas); // Se lee el mapa al que lleva la puerta. } else error(2, mapactual); break; case 2: // El personaje ha abierto el menú update = false; updatemap = true; pjmenu(controles, &personaje, items, mapactual, graph, VISION); break; case 3: // El personaje ha abierto el menú de administrador. update = false; updatemap = true; adminmenu(&VISION, &graph, &controles, &personaje); break; case 4: update = false; updatemap = false; break; case 5: update = false; updatemap = true; break; case 6: update = true; updatemap = true; break; default: // El personaje se ha movido a un terreno normal. break; } } while (1); }
std::pair<int, int> simulacion(int bloques, int bloque_size, int vias, int accesos, int pagina_size) { int paginas_disco, paginas_mem, fallos_pagina, fallos_cache, bits_offset, div_virt, div_fisica; std::cout << "Numero de bloques: " << bloques << std::endl; std::cout << "Tamano de bloque: " << bloque_size << std::endl; std::cout << "Numero de vias: " << vias << std::endl; std::cout << "Numero de accesos: " << accesos << std::endl; std::cout << "Tamanio de pagina: " << pagina_size << std::endl; std::cout << "Inicializando..."; std::random_device rseed; // Para numeros aleatorios std::mt19937 rgen(rseed()); // mersenne_twister std::uniform_int_distribution<int> idist(0, DIR_VIRUTALES - 1); // [0,4095] std::uniform_int_distribution<int> odist(0, 1); // [0,1] std::uniform_int_distribution<int> ddist(0, 255); // [0,255] std::uniform_int_distribution<int> nueva_dist(256, 511); // [0,255] /* ins_virtuales[*][x], x: 0 - direccion, 1 - lectura/escritura, 2 - dato */ std::vector<std::vector<int> > ins_virtuales (accesos, std::vector<int> (3,0)); std::vector<int> memoria (POS_MEMORIA); std::vector<int> disco (POS_DISCO); t_tabla tabla; /* Creamos la cache */ Cache mem_cache (vias, bloques, bloque_size); /* Inicializacion */ paginas_disco = POS_DISCO / pagina_size; paginas_mem = POS_MEMORIA / pagina_size; std::uniform_int_distribution<int> mdist(0, paginas_mem-1); // [0,paginas_memoria] fallos_pagina = 0; fallos_cache = 0; bits_offset = bits_para(pagina_size); div_virt = potencia(bits_offset);// para posterior division div_fisica = potencia(bits_para(bloque_size));// para posterior division std::cout << " Inicializacion terminada!" << std::endl; std::cout << "Paginas Memoria: " << paginas_mem << std::endl; std::cout << "Paginas Disco: " << paginas_disco << std::endl; std::cout << "Generando instrucciones..." << std::endl; /* Generar instrucciones virtuales */ for (int i = 0; i < accesos; ++i) { ins_virtuales[i][0] = idist(rgen); ins_virtuales[i][1] = odist(rgen); ins_virtuales[i][2] = nueva_dist(rgen); } std::cout << " Terminado!" << std::endl; std::cout << "Generando tabla de traduccion..." << std::endl; /* Generamos la tabla de traduccion */ int contador; for (contador = 0; contador < accesos; ++contador) { int tmp = ins_virtuales[contador][0]/div_virt; if(tabla.size() > paginas_mem) break; if(tabla.count(tmp) == 0) { tabla[tmp].push_back(odist(rgen)); /* 1 - memoria principal */ tabla[tmp].push_back(0); /* 1 - dato en disco mem llena */ tabla[tmp].push_back(contador); /* dir fisica */ } } for (; contador < accesos; ++contador) { int tmp = ins_virtuales[contador][0]/div_virt; if(tabla.size() >= (paginas_mem + paginas_disco)) break; if(tabla.count(tmp) == 0) { tabla[tmp].push_back(0); /* 1 - memoria principal */ tabla[tmp].push_back(1); /* 1 - dato en disco mem llena */ tabla[tmp].push_back(contador); /* dir disco */ } } std::cout << " Terminado!" << std::endl; std::cout << " Tamaño tabla: " << tabla.size() << std::endl; /* leemos la memoria y el disco */ std::ifstream inputmem; std::ifstream inputdisc; std::string outmem; std::string outdisc; int valor_io; int contador_io = 0; std::cout << "Leyendo memoria..." << std::endl; inputmem.open("memoria.txt", std::ifstream::in); while(inputmem >> valor_io) { memoria[contador_io] = valor_io; contador_io++; } inputmem.close(); std::cout << " Terminado!" << std::endl; if (contador_io == 0) { std::cout << "Memoria vacia, abortando!" << std::endl; return std::make_pair(0,0); } std::cout << "Leyendo disco..." << std::endl; inputdisc.open("disco.txt", std::ifstream::in); contador_io = 0; while(inputdisc >> valor_io) { disco[contador_io] = valor_io; contador_io++; } inputdisc.close(); std::cout << " Terminado!" << std::endl; if (contador_io == 0) { std::cout << "Disco vacio, abortando!" << std::endl; return std::make_pair(0,0); } std::cout << "Procesando instrucciones..." << std::endl; /* Iteramos en cada instruccion */ int dir_fisica, tmp, tmp2; std::vector<int> movimiento (bloque_size,0); std::vector<int> respuesta_cache; for (int i = 0; i < accesos; ++i) { /* Traducimos direccion virtual a fisica */ dir_fisica = ins_virtuales[i][0]/div_virt; /* No esta en memoria principal? */ if(tabla[dir_fisica][0] == 0) { //std::cout << "Fallo Pagina!" << std::endl; tabla[dir_fisica][0] = 1; fallos_pagina++; // nuevo fallo de pagina tmp2 = tabla[dir_fisica][2]; // direccion disco /* no esta asigana? */ if(tabla[dir_fisica][1] == 1) { tabla[dir_fisica][1] = 0; tmp = mdist(rgen); // nueva asignacion. tabla[dir_fisica][2] = tmp; /* Movemos de disco a memoria */ } else tmp = tmp2; // Si esta asignada disco - memoria concuerdan. tmp = tmp * div_virt; tmp2 = tmp2 * div_virt; for(int j = 0; j < pagina_size; ++j) { memoria[tmp + j] = disco[tmp2 + j]; } } /* El dato ya esta en memoria principal */ /* Extraemos direccion fisica */ dir_fisica = tabla[dir_fisica][2] * div_virt; /* Agregamos el offset */ dir_fisica = dir_fisica + (ins_virtuales[i][0] % div_virt); /* Cargamos los datos que hay en la memoria por si hay un miss en cache */ tmp = dir_fisica - (dir_fisica % div_fisica); // quitamos el offset de un bloque. for (int j = 0; j < bloque_size; ++j) { movimiento[j] = memoria[tmp + j]; } /* Lectura o escritura */ if (ins_virtuales[i][1] == 0) { //std::cout << "Read" << std::endl; respuesta_cache = mem_cache.read_cache(dir_fisica, movimiento); } else { //::cout << "Write" << std::endl; respuesta_cache = mem_cache.write_cache(dir_fisica, movimiento, ins_virtuales[i][2]); } /* Analimamos la respuesta de la cache */ /* no fue un hit? */ if(respuesta_cache[0] != 1) fallos_cache++; /* hay que escribir en memoria, por write-back? */ if (respuesta_cache[1] == 1) { //std::cout << "write-back" << std::endl; tmp = respuesta_cache[2]; // donde, escribir tmp = tmp - (tmp % div_fisica); // quitamos el offset del bloque. for (int j = 0; j < bloque_size; ++j) { memoria[tmp + j] = respuesta_cache[3+j]; } } } std::cout << " Terminado!" << std::endl; std::cout << "Reescribiendo memoria..." << std::endl; /* Excribimos en los archivos */ std::ofstream ofm ("memoria.txt", std::ofstream::out); for (int i = 0; i < POS_MEMORIA; ++i) { ofm << memoria[i] << "\n"; } ofm.close(); std::cout << "Terminado!" << std::endl; std::cout << "Reescribiendo disco..." << std::endl; std::ofstream ofd ("disco.txt", std::ofstream::out); for (int i = 0; i < POS_DISCO; ++i) { ofd << disco[i] << "\n"; } ofd.close(); std::cout << "Terminado!" << std::endl; std::cout << fallos_pagina << " " << fallos_cache << std::endl; return std::make_pair(fallos_pagina, fallos_cache); }