Juego del Gato en C

junio 28 20094 comentarios

Guardado en : General

Juego del Gato en C.

/*Juego de Gato Heurístico
  Autor:Jesús M.Olivares Ceja
  Desarrollado para propósitos didácticos de Ingeniería del Conocimiento
  Su copia es libre, si lo utiliza para propósitos no lucrativos.
*/
#include "stdio.h"
#include "dos.h"
#define SI  1
#define NO  0
  // TIPOS
  typedef struct {
  char tablero[9];
  int f;
} TipoTablero;
	//VARIABLES
struct
{
  TipoTablero Tm;
  int g;
  int UTc;
  TipoTablero Tc[7];
} arbol[8];
int UTiradaMaq;
TipoTablero juego;
char Linea[100];
	// PROTOTIPOS
void desplegaTablero (void);
int esValida (int tirada);
void generaTiradasMaq (void);
void generaTiradasContrario (int iTiradaMaq);
void creaTiradaMaq (int i);
void creaTc (int iTiradaMaq, int i);
void CalculaF (TipoTablero * t);
int revisaFin (int max);
void
main (void)
{
  int fin, valida, tiradaContrario, i;
  int iTiradaMaq, iTiradaContrario;
  int min, max, cualTm, vacias;
  // INICIALIZA EL TABLERO DE JUEGO
  for (i = 0; i < 9; i++)
    juego.tablero[i] = ' ';
  // MIENTRAS NO SEA FIN JUEGA
  fin = NO;
  while (fin == NO)
    {
      desplegaTablero ();
      // TOMA LA TIRADA DEL CONTRARIO HASTA QUE SEA VALIDA
      valida = NO;
      while (valida == NO)
	{
	  printf ("¿Donde tiras? [1..9]                0 = salir?\n");
	  gets (Linea);
	  tiradaContrario = atoi (Linea) - 1;
	  valida = esValida (tiradaContrario);
	  switch (valida)
	    {
	    case 0:
	      fin = SI;
	      valida = SI;
	      break;
	    case 1:
	      valida = SI;
	      break;
	    case 2:
	      printf ("Posición Ocupada, indica otra\n");
	      valida = NO;
	      break;
	    case 3:
	      printf ("Posición Erronea, indica otra [1..9]\n");
	      valida = NO;
	      break;
	    }
	}			// SI DECIDIO  TERMINAR, SALIRSE        
      if (fin == SI)
	continue;		// COLOCA LA TIRADA DEL CONTRARIO        
      juego.tablero[tiradaContrario] = ' ';
      desplegaTablero ();
      CalculaF (&juego);
      if (juego.f < -9000)
	{
	  printf ("Ganaste\n");
	  fin = SI;
	  continue;
	}			// GENERA POSIBLES TIRADAS DE LA MAQUINA
      UTiradaMaq = 0;
      generaTiradasMaq ();
      // PARA CADA TIRADA DE LA MAQUINA
      for (iTiradaMaq = 0; iTiradaMaq < UTiradaMaq; iTiradaMaq++)
	{
	  // GENERA POSIBLES TIRADAS DEL CONTRARIO            
	  arbol[iTiradaMaq].UTc = 0;
	  generaTiradasContrario (iTiradaMaq);
	  min = 15000;
	  // PARA CADA TIRADA DEL CONTRARIO            
	  for (iTiradaContrario = 0;
	       iTiradaContrario < arbol[iTiradaMaq].UTc; iTiradaContrario++)
	    {
	      // CALCULA F                
	      CalculaF (&arbol[iTiradaMaq].Tc[iTiradaContrario]);
	      // ENCUENTRA LA F MINIMA                
	      if (min > arbol[iTiradaMaq].Tc[iTiradaContrario].f)
		min = arbol[iTiradaMaq].Tc[iTiradaContrario].f;
	    }
	  // CALCULA F'            
	  CalculaF (&arbol[iTiradaMaq].Tm);
	  // CALCULA G            
	  arbol[iTiradaMaq].g = arbol[iTiradaMaq].Tm.f + min;
	}
      max = -15000;
      // ELIGE TM MEDIANTE EL CRITERIO G MAXIMA        
      cualTm = -1;
      for (iTiradaMaq = 0; iTiradaMaq < UTiradaMaq; iTiradaMaq++)
	{
	  if (arbol[iTiradaMaq].g > max)
	    {
	      cualTm = iTiradaMaq;
	      max = arbol[iTiradaMaq].g;
	    }
	}
      // SI LA MAQUINA TIRO        
      if (cualTm > -1)
	{
	  printf ("voy a tirar...\n");
	  delay (1000);
	  // COPIA EL TABLERO CON LA JUGADA DESEADA            
	  for (i = 0; i < 9; i++)
	    juego.tablero[i] = arbol[cualTm].Tm.tablero[i];
	}
      // DETERMINA LA SITUACION ACTUAL DEL JUEGO        
      CalculaF (&juego);
      switch (revisaFin (juego.f))
	{
	case 0:
	  break;		// CONTINUA        
	case 1:
	  desplegaTablero ();
	  printf ("LO SIENTO, Gane!!!!\n");
	  fin = SI;
	  break;
	case 2:
	  desplegaTablero ();
	  printf ("Ganaste\n");
	  fin = SI;
	  break;
	case 3:
	  printf ("Quedamos   G a t o, hagamos otro intento\n");
	  fin = SI;
	  break;
	}
    }
}
 
void
desplegaTablero (void)
{
  int r, c;
  for (r = 0; r < 3; r++)
    {
      for (c = 0; c < 3; c++)
	if (juego.tablero[3 * r + c] == 32)
	  printf ("%d  ", 3 * r + c + 1);
	else
	  printf ("%c  ", juego.tablero[3 * r + c]);
      printf ("\n\n");
    }
}
 
int
esValida (int tirada)
{
  if (tirada == -1)
    return 0;			// NO CONTINUAR    
  if ((tirada > -1) && (tirada < 9))
    if (juego.tablero[tirada] == ' ')
      return 1;
    else
      return 2;
  // POSICION OCUPADA
  else
    return 3;			// POSICION INVALIDA
}
 
void
generaTiradasMaq (void)
{
  int i;
  for (i = 0; i < 9; i++)
    if (juego.tablero[i] == ' ')
      creaTiradaMaq (i);
}
 
void
generaTiradasContrario (int iTiradaMaq)
{
  int i;
  for (i = 0; i < 9; i++)
    if (arbol[iTiradaMaq].Tm.tablero[i] == ' ')
      creaTc (iTiradaMaq, i);
}
 
void
creaTiradaMaq (int i)
{
  int k;
  for (k = 0; k < 9; k++)
    arbol[UTiradaMaq].Tm.tablero[k] = juego.tablero[k];
  arbol[UTiradaMaq].Tm.tablero[i] = 'o';
  UTiradaMaq++;
}
 
void
creaTc (int iTiradaMaq, int i)
{
  int k;
  for (k = 0; k < 9; k++)
    arbol[iTiradaMaq].Tc[arbol[iTiradaMaq].UTc].tablero[k] =
      arbol[iTiradaMaq].Tm.tablero[k];
  arbol[iTiradaMaq].Tc[arbol[iTiradaMaq].UTc].tablero[i] = 'x';
  arbol[iTiradaMaq].UTc++;
}
 
void
CalculaF (TipoTablero * t)
{
  int v, h, d;
  int r, c, ctaO, ctaE, ctaX;
  // SUMA LAS VERTICALES MAQUINA
  v = 0;
  for (c = 0; c < 3; c++)
    {
      ctaO = 0;
      ctaE = 0;
      for (r = 0; r < 3; r++)
	{
	  if (t->tablero[3 * r + c] == 'o')
	    ctaO++;
	  if (t->tablero[3 * r + c] == ' ')
	    ctaE++;
	}
      if (ctaO == 3)
	{
	  t->f = 9999;
	  return;
	}
      if ((ctaO + ctaE) == 3)
	v++;
    }
  h = 0;
  for (r = 0; r < 3; r++)
    {
      ctaO = 0;
      ctaE = 0;
      for (c = 0; c < 3; c++)
	{
	  if (t->tablero[3 * r + c] == 'o')
	    ctaO++;
	  if (t->tablero[3 * r + c] == ' ')
	    ctaE++;
	}
      if (ctaO == 3)
	{
	  t->f = 9999;
	  return;
	}
      if ((ctaO + ctaE) == 3)
	h++;
    }				// SUMA LAS DIAGONALES MAQUINA    
  d = 0;
  ctaO = 0;
  ctaE = 0;
  for (c = 0; c < 9; c += 4)
    {
      if (t->tablero[c] == 'o')
	ctaO++;
      if (t->tablero[c] == ' ')
	ctaE++;
    }
 
  if (ctaO == 3)
    {
      t->f = 9999;
      return;
    }
  if ((ctaO + ctaE) == 3)
    d++;
  ctaO = 0;
  ctaE = 0;
  for (c = 2; c < 7; c += 2)
    {
      if (t->tablero[c] == 'o')
	ctaO++;
      if (t->tablero[c] == ' ')
	ctaE++;
    }
 
  if (ctaO == 3)
    {
      t->f = 9999;
      return;
    }
  if ((ctaO + ctaE) == 3)
    d++;
  // SUMA LAS VERTICALES CONTRARIO    
  for (c = 0; c < 3; c++)
    {
      ctaX = 0;
      ctaE = 0;
      for (r = 0; r < 3; r++)
	{
	  if (t->tablero[3 * r + c] == 'x')
	    ctaX++;
	  if (t->tablero[3 * r + c] == ' ')
	    ctaE++;
	}
      if (ctaX == 3)
	{
	  t->f = -9999;
	  return;
	}
      if ((ctaX + ctaE) == 3)
	v--;
    }
 
  // SUMA LAS HORIZONTALES CONTRARIO    
  for (r = 0; r < 3; r++)
    {
      ctaX = 0;
      ctaE = 0;
      for (c = 0; c < 3; c++)
	{
	  if (t->tablero[3 * r + c] == 'x')
	    ctaX++;
	  if (t->tablero[3 * r + c] == ' ')
	    ctaE++;
	}
      if (ctaX == 3)
	{
	  t->f = -9999;
	  return;
	}
      if ((ctaX + ctaE) == 3)
	h--;
    }
 
  // SUMA LAS DIAGXNALES CONTRARIO    
  ctaX = 0;
  ctaE = 0;
  for (c = 0; c < 9; c += 4)
    {
      if (t->tablero[c] == 'x')
	ctaX++;
      if (t->tablero[c] == ' ')
	ctaE++;
    }
 
  if (ctaX == 3)
    {
      t->f = -9999;
      return;
    }
  if ((ctaX + ctaE) == 3)
    d--;
  ctaX = 0;
  ctaE = 0;
  for (c = 2; c < 7; c += 2)
    {
      if (t->tablero[c] == 'x')
	ctaX++;
      if (t->tablero[c] == ' ')
	ctaE++;
    }
 
  if (ctaX == 3)
    {
      t->f = -9999;
      return;
    }
  if ((ctaX + ctaE) == 3)
    d--;
  // ASIGNA F    
  t->f = v + h + d;
}
 
int
revisaFin (int max)
{
  int i, vacias;
  if (max > 9000)
    return 1;
  // GANO LA MAQUINA
  if (max < -9000)
    return 2;
  // GANO EL CONTRARIO
  vacias = 0;
  for (i = 0; i < 9; i++)
    if (juego.tablero[i] == ' ')
      vacias++;
  if (vacias > 0)
    return 0;
  // PUEDEN CONTINUAR
  return 3;
  // SE ACABO EL JUEGO FUE GATO
}
 
	// fin del archivo

Quizá te interese :

Acerca del autor:

4 Respuestas a “Juego del Gato en C”

  1. carlos dice:

    Hola amigo, me tira los siguientes errores el codigo;
    33 C:\Documents and Settings\Administrador\Escritorio\main.cpp `main’ must return `int’
    C:\Documents and Settings\Administrador\Escritorio\main.cpp In function `int main(…)’:
    52 C:\Documents and Settings\Administrador\Escritorio\main.cpp `atoi’ undeclared (first use this function)
    (Each undeclared identifier is reported only once for each function it appears in.)
    123 C:\Documents and Settings\Administrador\Escritorio\main.cpp `delay’ undeclared (first use this function)
    C:\Documents and Settings\Administrador\Escritorio\Makefile.win [Build Error] [main.o] Error 1

    Que tengo que arreglar?
    no entiendo mucho

  2. Daniel dice:

    Saludos Carlos
    El código es para BorlandC para DOS, creo que lo quieres compilar para gcc.
    Para que sea compatible tendrías que hacerle los siguientes cambios:

    • El código ponerlo en un proyecto de lenguaje C para consola
    • Cambiar el tipo de la función main de void a int y agregar un return 0
    • Incluir stdlib.h y string.h a tu código

    Espero te ayude

  3. Luis dice:

    H o l a a!

    Oye me sale un error en ” delay (1000); ”
    lo estoy compilando en Borland C++

    Por favor si me podrias ayudar en eso…

    Saludos! ^^

  4. Daniel dice:

    Puedes quitar esa línea y retirar también:

    #include

    Eso no es obligatorio para el funcionamiento del programa, solo es para dar la impresión de que el programa “piense”.

Deja un comentario


Licencia y uso

Las técnicas demostradas en los tutoriales pueden ser utilizadas sin ninguna limitación y tampoco es obligatorio dar una atribución.


Los textos, imágenes y tutoriales son propiedad de sus respectivos autores, nuestro contenido se encuentra bajo licencia Creative Commons Share-Alike.

Escribe algo para el sitio

El escribir un tutorial o un artículo, mandarnos un enlace para Ubicuos, no solamente es una forma de obtener publicidad, si no también de dar algo a la comunidad y nosotros te lo recompensamos con los premios del mes! Leer más de nuestras promociones

¿Sugerencias?

Este es TU sitio, si tienes sugerencias o ideas de cómo podemos mejorarlo para ti, ¡Por favor háznoslos saber!

Hacemos nuestro mayor esfuerzo en proporcionar un sitio útil y amigable y esperamos que disfrutes tu tiempo aquí.

Ayuda a Difundir

Te gusta Ubicuos?

Ve las formas en que nos puedes apoyar.

Apoyando a Ubicuos.com

Submit your linkClose

-->