Primero empecemos por el de DS, ese fue un reto el codigo fuente es este:
#include
#include "all_gfx.h"
int TIEMPO_ESPERA =0;
int salida = 4; // 0 = tiempos, 1 = estatus , 2 = comen, 3 = pausa
int imprimir = 1;
int salx = 8;
int saly = 6;
struct filosofo{
int tiempo;
int espera;
int estatus; //0 = asignar tiempo, 1 = quiero comer , 2 = comiendo, 3 = termine de comer
};
struct filosofo filo[5];
void salida_debug(){
switch (salida){
int x =0;
case 0: //tiempos
for (x=0;x<=750;x++){
PA_OutputText(0,x,0," ");
}
for(x=0;x<=4;x++){
PA_OutputText(0,8,x+6,"Tiempo falta: %d ",filo[x].espera );
}
saly = 6;
imprimir = 1;
break;
case 1: //estatus
imprimir = 1;
saly = 6;
for (x=0;x<=750;x++){
PA_OutputText(0,x,0," ");
}
for(x=0;x<=4;x++){
PA_OutputText(0,8,x+6,"Estatus: Filo[%d] %d ",x,filo[x].estatus );
}
PA_OutputText(0,8,12,"Estatus del Semaforo");
PA_OutputText(0,8,14,"0 = Asig. de Tiempo");
PA_OutputText(0,8,15,"1 = Quiero comer");
PA_OutputText(0,8,16,"2 = Comiendo");
PA_OutputText(0,8,17,"3 = Soltare ");
break;
case 2: //comen
salx = 8;
if (saly > 19){
saly = 6;
for (x=0;x<=750;x++){
PA_OutputText(0,x,0," ");
}
}
imprimir = 0;
break;
case 3: //pausa
break;
}
}
void iniciar_sprites(){
PA_EasyBgLoad(1, 0, mesa);
PA_EasyBgLoad(0, 1, menu);
PA_LoadSpritePal(1,0,(void*)mole_Pal);
PA_LoadSpritePal(1,1,(void*)conte_Pal);
PA_LoadSpritePal(1,2,(void*)tene_Pal);
PA_LoadSpritePal(0,1,(void*)flecha_Pal);
PA_CreateSprite(1,0,(void*)mole_Sprite,OBJ_SIZE_64X64,1,0,96, 0); // mole 0
PA_CreateSprite(1,1,(void*)mole_Sprite,OBJ_SIZE_64X64,1,0,183, 43); // mole 1
PA_CreateSprite(1,2,(void*)mole_Sprite,OBJ_SIZE_64X64,1,0,185, 123); // mole 2
PA_CreateSprite(1,3,(void*)mole_Sprite,OBJ_SIZE_64X64,1,0,7, 123); // mole 3
PA_CreateSprite(1,4,(void*)mole_Sprite,OBJ_SIZE_64X64,1,0,7, 30); // mole 4
PA_CreateSprite(1,5,(void*)conte_Sprite,OBJ_SIZE_64X64,1,1,300, 300); // conte 0
PA_CreateSprite(1,6,(void*)conte_Sprite,OBJ_SIZE_64X64,1,1,300, 300); // conte 1
PA_CreateSprite(1,7,(void*)conte_Sprite,OBJ_SIZE_64X64,1,1,300, 300); // conte 2
PA_CreateSprite(1,8,(void*)conte_Sprite,OBJ_SIZE_64X64,1,1,300, 300); // conte 3
PA_CreateSprite(1,9,(void*)conte_Sprite,OBJ_SIZE_64X64,1,1,300, 300); // conte 4
PA_CreateSprite(1,11,(void*)tene_Sprite,OBJ_SIZE_32X32,1,2,75, 45); //tene1
PA_CreateSprite(1,12,(void*)tene_Sprite,OBJ_SIZE_32X32,1,2,150, 45); //tene1
PA_SetSpriteRotEnable(1,12,0); //rotacion
PA_SetRotsetNoZoom(1,0,430);
PA_CreateSprite(1,13,(void*)tene_Sprite,OBJ_SIZE_32X32,1,2,190, 100); //tene1
PA_SetSpriteRotEnable(1,13,1); //rotacion
PA_SetRotsetNoZoom(1,1,360);
PA_CreateSprite(1,14,(void*)tene_Sprite,OBJ_SIZE_32X32,1,2,110, 130); //tene1
PA_CreateSprite(1,15,(void*)tene_Sprite,OBJ_SIZE_32X32,1,2,30, 90); //tene1
PA_SetSpriteRotEnable(1,15,3); //rotacion
PA_SetRotsetNoZoom(1,3,90);
PA_CreateSprite(0,1,(void*)flecha_Sprite,OBJ_SIZE_32X32,1,1,20, 33);
}
void poner_blanca (){
int x = 0;
for (x=(-31);x<=0;x++){
PA_WaitForVBL();
PA_SetBrightness(1,x);
PA_SetBrightness(0,x);
}
}
void poner_negra (){
int x = 0;
for (x=0;x<=31;x++){
PA_WaitForVBL();
PA_SetBrightness(1,0 -x);
PA_SetBrightness(0,0 -x);
}
}
int main(int argc, char ** argv)
{
PA_Init();
PA_InitVBL();
PA_UpdateRTC();
//declaracion de procesos filosofos
//id,time,esperar RND();,estatus
//inicializar los filosofos con numeros aleatoreos
PA_InitRand();
//cargar sprites
//iniciar carga de
// Initialise the text system on the top screen
PA_InitText(0,0);
PA_SetTextCol(0,0,0,0);
PA_SetBrightness(0,-31);
PA_SetBrightness(1,-31);
PA_EasyBgLoad(1, 0, intro);
PA_EasyBgLoad(0, 1, intro0);
poner_blanca();
PA_WaitForVBL();
while(1){
PA_WaitForVBL();
if (Stylus.Newpress){
break;
}
}
poner_negra();
iniciar_sprites();
PA_OutputText(0,8,6,"Iniciando Filosofos..");
iniciar_filosofos();
PA_OutputText(0,8,7,"Asig. tiempos RND().");
asignar_tiempo_espera();
PA_OutputText(0,8,8,"Iniciar Algoritmo...");
poner_blanca();
int x =0;
while (1){
salida_debug();
if (Stylus.Newpress)
{
//PA_SetSpriteXY(screen, sprite, Stylus.X, Stylus.Y);
if (((Stylus.X>41)&&(Stylus.X<105 amp="" stylus.y="">4)&&(Stylus.Y<26 div="">26>105>
salida = 0;
}
if (((Stylus.X>106)&&(Stylus.X<153 amp="" stylus.y="">4)&&(Stylus.Y<26 div="">26>153>
salida = 1;
}
if (((Stylus.X>154)&&(Stylus.X<226 amp="" stylus.y="">4)&&(Stylus.Y<26 div="">26>226>
salida = 2;
}
}
if ((Stylus.X > 51)&&(Stylus.X<>41)&&(Stylus.Y<165 div="">165>
//pausa !
while(1){
PA_WaitForVBL();
if (!Stylus.Held){
break;
}
}
}
if (Stylus.Held){
if ( PA_SpriteTouched(1)){
if ((Stylus.Y > 30)&&(Stylus.Y<>
PA_SetSpriteXY (0,1,20,Stylus.Y - 8);
TIEMPO_ESPERA = (Stylus.Y / 16);
if ( TIEMPO_ESPERA < tiempo_espera =" 0;
}
}
}
for (x=0;x<= TIEMPO_ESPERA ;x++){
PA_WaitForVBL();
}
//PA_OutputText(0,0,y,"Tiempo: %d",PA_Rand());
//y++;
for (x=0;x<=4;x++){
filo[x].espera--;
if (filo[x].espera <= 0){
evaluar_Acciones(x);
}
}
}
return 0;
} // End of main()
void iniciar_filosofos(){
int x=0;
for (x=0;x<=4;x++){
filo[x].estatus = 0;
filo[x].tiempo = 0;
filo[x].espera = 0;
}
}
void asignar_tiempo_espera(){
int x;
for (x=0;x<=4;x++){
if (filo[x].estatus == 0){
filo[x].espera = (PA_Rand() / PA_Rand());
if (filo[x].espera > 100 ) {
filo[x].espera = 60;
}
}
}
}
void evaluar_Acciones(int id){
asignar_tiempo_filo(id);
switch(filo[id].estatus){
case 0:
filo[id].estatus = 1;
break;//asignar tiempo
case 1: //1= quiero comer
switch(id){ //evaluar si puede comer
case 0:
if ((filo[1].estatus == 1 )&&(filo[4].estatus == 1 )){
//si COME !!!
//PA_OutputText(0,0,y,"COME %d...",id);
come_sprite(id);
filo[1].estatus = 0;
filo[4].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 1:
if ((filo[0].estatus == 1 )&&(filo[2].estatus == 1 )){
//si COME !!!
come_sprite(id);
// PA_OutputText(0,0,y,"COME %d...",id);
filo[0].estatus = 0;
filo[2].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 2:
if ((filo[1].estatus == 1 )&&(filo[3].estatus == 1 )){
//si COME !!!
come_sprite(id);
//PA_OutputText(0,0,y,"COME %d...",id);
filo[1].estatus = 0;
filo[3].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 3:
if ((filo[4].estatus == 1 )&&(filo[2].estatus == 1 )){
//si COME !!!
come_sprite(id);
//PA_OutputText(0,0,y,"COME %d...",id);
filo[2].estatus = 0;
filo[4].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 4:
if ((filo[3].estatus == 1 )&&(filo[0].estatus == 1 )){
//si COME !!!
come_sprite(id);
//PA_OutputText(0,0,y,"COME %d...",id);
filo[3].estatus = 0;
filo[0].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
}
break;//quiero comer
case 2:
filo[id].estatus = 3;
break;//comiendo
case 3:
termine_sprite(id);
filo[id].estatus = 0;
break;//termine de comer
}
}
void asignar_tiempo_filo(int id){
//PA_InitRand();
filo[id].espera = (PA_Rand() / PA_Rand() ) ;
if (filo[id].espera > 100 ) {
filo[id].espera = 60;
}
}
void come_sprite(int id){
int x = 0;
int y = 0;
switch (id){
case 0:
x = 96;
y = 0;
break;
case 1:
x = 183;
y = 43;
break;
case 2:
x = 185;
y = 123;
break;
case 3:
x = 7;
y = 123;
break;
case 4:
x = 7;
y = 30;
break;
}
PA_SetSpriteXY(1,id,300,300);
PA_SetSpriteXY(1,id+5,x,y);
//mover tenedores correspondientes
int ten1 = 0;
int ten2 =0;
int x1 = 0;
int y1 = 0;
int x2 = 0;
int y2 = 0;
switch (id){
case 0:
ten1 = 1;
ten2 = 2;
x1 = 75;
y1 = 25;
x2 = 170;
y2 = 25;
break;
case 1:
ten1 = 2;
ten2 = 3;
x1 = 170;
y1 = 25;
x2 = 210;
y2 = 100;
break;
case 2:
ten1 = 3;
ten2 = 4;
x1 = 210;
y1 = 100;
x2 = 110;
y2 = 150;
break;
case 3:
ten1 = 4;
ten2 = 5;
x1 = 110;
y1 = 150;
x2 = 10;
y2 = 90;
break;
case 4:
ten1 = 1;
ten2 = 5;
x1 = 75;
y1 = 25;
x2 = 10;
y2 = 90;
break;
}
PA_SetSpriteXY(1,ten1 + 10,x1,y1);
PA_SetSpriteXY(1,ten2 + 10,x2,y2);
if (imprimir ==0){
PA_OutputText(0,salx,saly,"COMI FILO[%d]....." , id );
salx++;
saly++;
}
}
void termine_sprite(int id){
int x = 0;
int y = 0;
switch (id){
case 0:
x = 96;
y = 0;
break;
case 1:
x = 183;
y = 43;
break;
case 2:
x = 185;
y = 123;
break;
case 3:
x = 7;
y = 123;
break;
case 4:
x = 7;
y = 30;
break;
}
PA_SetSpriteXY(1,id + 5,300,300);
PA_SetSpriteXY(1,id,x,y);
int ten1 = 0;
int ten2 =0;
int x1 = 0;
int y1 = 0;
int x2 = 0;
int y2 = 0;
switch (id){
case 0:
ten1 = 1;
ten2 = 2;
x1 = 75;
y1 = 45;
x2 = 150;
y2 = 45;
break;
case 1:
ten1 = 2;
ten2 = 3;
x1 = 150;
y1 = 45;
x2 = 190;
y2 = 100;
break;
case 2:
ten1 = 3;
ten2 = 4;
x1 = 190;
y1 = 100;
x2 = 110;
y2 = 130;
break;
case 3:
ten1 = 4;
ten2 = 5;
x1 = 110;
y1 = 130;
x2 = 30;
y2 = 90;
break;
case 4:
ten1 = 1;
ten2 = 5;
x1 = 75;
y1 = 45;
x2 = 30;
y2 = 90;
break;
}
PA_SetSpriteXY(1,ten1 + 10,x1,y1);
PA_SetSpriteXY(1,ten2 + 10,x2,y2);
if (imprimir ==0){
PA_OutputText(0,salx,saly,"Solte FILO[%d]....." , id );
salx++;
saly++;
}
}
como pueden ver es un poco extenso, esto es por que tiene integrado la interfas grafica del DS, por la animacion de los filosofos !
pero analizando el código podríamos concluir .... DEBE DE TENER UNA FORMA DE ANALIZIS DE LOS FILÓSOFOS, por lo tanto si analizamos el código podríamos ser capaces de extraer el motor que utiliza para los procesos de los filósofos, para fines mas prácticos y para ayudarlos a ahorrar tiempo aquí les entrego el código listo, ahí solo esta el motor de los filósofos, por lo tanto de esta manera seria mas fácil su entendimiento.
MOTOR DE LOS FILÓSOFOS:
#include //librerias para manejar el E/S
#include //libreria para imprimir
#include
int TIEMPO_ESPERA =0; //espera de los filosofos
int salida = 4; // 0 = tiempos, 1 = estatus , 2 = comen, 3 = pausa // estatus de ellos cada numero representa algo
struct filosofo{ //estructura de filosofos
int tiempo; //tiempo correspondiente
int espera; // cuanto tiempo tiene que esperar
int estatus; //0 = asignar tiempo, 1 = quiero comer , 2 = comiendo, 3 = termine de comer
};
struct filosofo filo[5]; //declaro 5 filosofos
int main(int argc, char ** argv)
{
iniciar_filosofos(); //inicialiso a los filosofos llamando a esta funcion
printf("Asig. tiempos RND().\n"); //imprimo este texto
asignar_tiempo_espera(); //aqui le asigno el tiempo aleatorio y el estatus a los filosofos int x =0; //declaro X
while (1){ //ciclo infinito por que se supone que nunca terminara
for (x=0;x<=4;x++){ //verifico los 5 filosofos (del 0 al 4 )
//la x representa cada filosofo por eso esta en un for
filo[x].espera--; //a cada uno le resto 1 en el tiempo que debe de esparar
if (filo[x].espera <= 0){ //en caso de que espera sea 0, ocea que ya debe de evaluar lo que debe hacer
evaluar_Acciones(x); //evaluo al filosofo
}
}
}
return 0;
} // termina el main
void iniciar_filosofos(){ //inicializa los filosofos
int x=0;
for (x=0;x<=4;x++){ //por cada filosofo se le asigna a 0 todo, es por eso que esta en un for, y x representa cada filosofo
filo[x].estatus = 0;
filo[x].tiempo = 0;
filo[x].espera = 0;
}
}
void asignar_tiempo_espera(){ //esta funcion asigna un tiempo aleatorio a cada filosofo
int x;
for (x=0;x<=4;x++){
if (filo[x].estatus == 0){ //en caso de que su estatus sea 0, verifica en la declaracion de filosofos el estatus
filo[x].espera = (rand() / rand()); //se le asigna un tiempo aleatorio
}
}
}
void evaluar_Acciones(int id){ //esta funcion evalua lo que debe hacer cada filosofo cuando tu espera termino, depende del estatus en que se encuentre es lo que hara es por eso que esta en un case !
asignar_tiempo_filo(id); //se le asigna un nuevo tiempo, el id es el id del filosofo
switch(filo[id].estatus){
case 0: //en caso de que sea asignar tiempo se le pone en 1 el estatus, por que ya se le asigno antes
filo[id].estatus = 1;
break;//asignar tiempo
case 1: //1= quiero comer
switch(id){ //evaluar si puede comer
case 0: si es el filosofo 0 entonces verifica al 1 y al 4, debes de hacer un diagrama para entenderlo mejor
if ((filo[1].estatus == 1 )&&(filo[4].estatus == 1 )){
//si COME !!!
printf("COME %d...\n",id); //imprime el texto COME con su ID
filo[1].estatus = 0;
filo[4].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 1:
if ((filo[0].estatus == 1 )&&(filo[2].estatus == 1 )){
//si COME !!!
printf("COME %d...\n",id);
filo[0].estatus = 0;
filo[2].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 2:
if ((filo[1].estatus == 1 )&&(filo[3].estatus == 1 )){
//si COME !!!
printf("COME %d...\n",id);
filo[1].estatus = 0;
filo[3].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 3:
if ((filo[4].estatus == 1 )&&(filo[2].estatus == 1 )){
//si COME !!!
printf("COME %d...\n",id);
filo[2].estatus = 0;
filo[4].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
case 4:
if ((filo[3].estatus == 1 )&&(filo[0].estatus == 1 )){
//si COME !!!
printf("COME %d...\n",id);
filo[3].estatus = 0;
filo[0].estatus = 0;
filo[id].estatus = 2;
}else{
//no come !! :(
}
break;
}
break;//quiero comer
case 2:
filo[id].estatus = 3;
break;//comiendo
case 3:
printf("Termine %d...\n",id);
filo[id].estatus = 0;
break;//termine de comer
}
}
void asignar_tiempo_filo(int id){
filo[id].espera = (rand() / rand() ) ;
}
WAAAA ! podemos ver que es mucho mas pequeño que el primero, esto es por que ahora ya no esta la interfaz gráfica del DS, cabe mencionar que el codigo creo que tiene un error logico, mas bien creo que le falta inicializar el RAND, pero eso es fácil de hacer, ahora bien aun falta algo...
Este código solamente es el motor, por lo tanto se requiere modificar y personalizar para que podamos entregar algo mas original :P, pero bueno SUERTE EN SU AVENTURA DE DESARROLLO !
Aqui les dejo los archivos:
Filosofos solo motor : DESCARGAR
Filosofos con interfaz DS : DESCARGAR
la próxima entrada sera de como codificarlo ! para adaptarlo como quieras ! :P
Agradecer no cuesta nada ! :P
SALUDOS !