Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: AlbertoBSD en 29 Agosto 2016, 14:56 pm



Título: Optimizar evaluación de juego de TATETI
Publicado por: AlbertoBSD en 29 Agosto 2016, 14:56 pm
Siguiendo con el tema de :

[C] Duda TATETI (http://foro.elhacker.net/programacion_cc/c_duda_tateti-t456724.0.html)

en ese tema puse un codigo para Generar un Arbol de N niveles apartir de una jugada inicial

Ahora toca evaluar todos los nodos (Juegos) para asi poder decidir el mejor movimiento

Dada las siguientes definiciones y estructuras:

Código
  1. #define UNKNOW 0 //Nobody win yet
  2. #define O_WIN 1
  3. #define X_WIN 2
  4. #define DRAW 3
  5. #define ERROR 4
  6.  
  7. struct tablero {
  8. uint8_t juego[3][3];
  9. };
  10.  

Hice esta funcion que evalua las 3 Filas , 3 Columnas y 2 Diagonales. Adicional evaluar si es empate, si todavia nadie gana y si existe alguna discrepancia en el tablero

La pregunta aqui es, ¿Existe una forma mas eficiente de hacer esto?

Me refiero a que se me hace bastante pesado evaluar todas las lineas xD..

NOTA: No he compilado el codigo por lo que puedw tener errores.

Código
  1. uint8_t estatus_juego(struct tablero *t) {
  2. uint8_t e;  //Estatus a devolver
  3. register uint8_t i = 0,j = 0;
  4. uint8_t contador_X,contador_O,casilla;
  5. bool continuar = true;
  6. //Procedemos a validar las 3 Lineas horizontales
  7. i = 0;
  8. while(continuar && i < 3) {
  9. j = 0;
  10. casilla = t->juego[i][j];
  11. j++;
  12. while(continuar && j < 3 && ) {
  13. if(casilla != t->juego[i][j] || !t->juego[i][j]) {
  14. continuar = false;
  15. }
  16. j++;
  17. }
  18. if(continuar){
  19. //si continuar sigue siendo true en este punto el jugador casilla Gana y ya no es necesario evaluar los otros casos
  20. continuar = false; // Establemos continuar como false para que ya no entre al ciclo siguiente
  21. }
  22. else {
  23. //En caso de que continuar sea false, significa que debemos seguir evaluando las lineas restantes
  24. continuar = true // Establemos continuar como true para que si entre al ciclo siguiente
  25. }
  26. i++;
  27. }
  28. if(continuar) {
  29. //Continuamos la evaluacion de las lineas Verticales
  30. i = 0;
  31. while(continuar && i < 3) {
  32. j = 0;
  33. casilla = t->juego[j][i];
  34. j++;
  35. while(continuar && j < 3) {
  36. if(casilla != t->juego[j][i] || !t->juego[j][i] ) {
  37. continuar = false;
  38. }
  39. j++;
  40. }
  41. if(continuar){
  42. //si continuar sigue siendo true en este punto el jugador casilla Gana y ya no es necesario evaluar los otros casos
  43. continuar = false; // Establemos continuar como false para que ya no entre al ciclo siguiente
  44. }
  45. else {
  46. //En caso de que continuar sea false, significa que debemos seguir evaluando las lineas restantes
  47. continuar = true // Establemos continuar como true para que si entre al ciclo siguiente
  48. }
  49. i++;
  50. }
  51. if(continuar) { //Evaluamos las lineas Diagonales
  52. casilla = t->juego[0][0];
  53. if(casilla == t->juego[1][1] && casilla == t->juego[2][2] && casilla != 0) {
  54. if(casilla == 'X') {
  55. e = X_WIN;
  56. }
  57. else {
  58. e = O_WIN;
  59. }
  60.  
  61. }
  62. else {
  63. casilla = t->juego[0][2];
  64. if(casilla == t->juego[1][1] && casilla == t->juego[2][0]  && casilla != 0) {
  65. if(casilla == 'X') {
  66. e = X_WIN;
  67. }
  68. else {
  69. e = O_WIN;
  70. }
  71. }
  72. else {
  73. //Todavia nadie gana o es empate en caso de que ya no queden casillas libres
  74. contador_X = 0;
  75. contador_O = 0;
  76. i = 0;
  77. while(i < 3) {
  78. j = 0;
  79. while(j < 3) {
  80. if(t->juego[i][j] == 'X') {
  81. contador_X++;
  82. }
  83. else {
  84. if(t->juego[i][j] == 'O') {
  85. contador_O++;
  86. }
  87. }
  88. j++;
  89. }
  90. i++;
  91. }
  92. if(abs(contador_O-contador_X) > 1) {
  93. //ERROR de Tablero, no es posible que un jugador tenga 2 o mas 'fichas' que el otro en el tablero
  94. e = ERROR;
  95. }
  96. else {
  97. if(contador_X+contador_O < 9) {
  98. e = UNKNOW;
  99. }
  100. else {
  101. e = DRAW;
  102. }
  103. }
  104. }
  105. }
  106. }
  107. else {
  108. //En este punto evaluamos quien gano
  109. if(casilla == 'X') {
  110. e = X_WIN;
  111. }
  112. else {
  113. e = O_WIN;
  114. }
  115. }
  116. }
  117. else {
  118. //En este punto evaluamos quien gano
  119. if(casilla == 'X') {
  120. e = X_WIN;
  121. }
  122. else {
  123. e = O_WIN;
  124. }
  125. }
  126. return e;
  127. }
  128.  

Saludos


Título: Re: Optimizar evaluación de juego de TATETI
Publicado por: HardForo en 3 Septiembre 2016, 00:20 am
Segun la Wikipedia se puede programar un jugador perfecto, inclusive proveen las reglas para el juego "perfecto", seguro puedes hacer que juegue bien (primero el centro, luego la preferencia son las esquinas,...) pero si has seguido ese algoritmo tu IA o gana o empata  ;D

https://en.wikipedia.org/wiki/Tic-tac-toe

Por cierto, se ve muy bien tu código.