C 4 Gewinnt, Gewinnabfrage frage

suxido

Newbie
Registriert
Juni 2013
Beiträge
1
Hallo,

Ich muss für die Schule ein 4 Gewinnt Spiel programmieren. Bis jetzt ists ganz Ok. Ich bin ziemlich zufrieden mit meiner Arbeit. Eigentlich ist es jetzt schon fertig, wenn man selber schaut wer gewonnen hat.

ABER, wäre es nicht toll wenn das der Computer machen würde? Doch, und genau das will ich machen. Nur leider häng ich da jetzt gerade fest. Ich komm einfach nicht drauf wie ich es überprüfen lassen soll ob 4 in der gleichen Reihe sind. Ich wäre schon dankbar wenn ich erst mal horizontal und vertikal prüfen könnte :D

Hier ist mal mein Code:

Code:
// 4_Gewinnt.cpp : Definiert den Einstiegspunkt für die Konsolenanwendung.
//

#include "stdafx.h"
#include <stdio.h>
#include <stdlib.h>


int main()
{
	//Variabeldefinitionen
	char Spielfeld[8][8];
	char SpielerA = 'A';
	char SpielerB = 'X';
	int SpielerEingabe1 = 0;
	int SpielerEingabe2 = 0;
	int ZaehlerA = 0;
	int ZaehlerB = 0;
	int GewinnerA = 0;
	int GewinnerB = 0;
	int xyz = 1;

	//printf("Vier Gewinnt\n");
	//printf("by Marco Laim\n\n\n");
	
	//Alle Felder mit einem Unterstrich füllen damit es einheitlich aussieht
	for(int i=0;i<=7;i++)
	{
		for(int fuellen=0;fuellen<=7;fuellen++)
		{
			Spielfeld[i][fuellen] = '_';
		}
	}

	//Spielfeld[0][4] = 'A';
	//Spielfeld[2][7] = 'X';
	do
	{
	printf("Vier Gewinnt\n");
	printf("by Me\n\n\n");
	
	//Gewinnprüfung
	for(int i=0;i<=7;i++)
	{
		int counter = 0;
		for(int j=0;j<=7;j++)
		{
			//Spielfeld[i][j] = SpielerA;
		}
	}





	//Ausgabe Spielfeld
	printf("    0   1   2   3   4   5   6   7\n");
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("0 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[0][0],Spielfeld[0][1],Spielfeld[0][2],Spielfeld[0][3],Spielfeld[0][4],Spielfeld[0][5],Spielfeld[0][6],Spielfeld[0][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("1 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[1][0],Spielfeld[1][1],Spielfeld[1][2],Spielfeld[1][3],Spielfeld[1][4],Spielfeld[1][5],Spielfeld[1][6],Spielfeld[1][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("2 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[2][0],Spielfeld[2][1],Spielfeld[2][2],Spielfeld[2][3],Spielfeld[2][4],Spielfeld[2][5],Spielfeld[2][6],Spielfeld[2][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("3 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[3][0],Spielfeld[3][1],Spielfeld[3][2],Spielfeld[3][3],Spielfeld[3][4],Spielfeld[3][5],Spielfeld[3][6],Spielfeld[3][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("4 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[4][0],Spielfeld[4][1],Spielfeld[4][2],Spielfeld[4][3],Spielfeld[4][4],Spielfeld[4][5],Spielfeld[4][6],Spielfeld[4][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("5 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[5][0],Spielfeld[5][1],Spielfeld[5][2],Spielfeld[5][3],Spielfeld[5][4],Spielfeld[5][5],Spielfeld[5][6],Spielfeld[5][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("6 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[6][0],Spielfeld[6][1],Spielfeld[6][2],Spielfeld[6][3],Spielfeld[6][4],Spielfeld[6][5],Spielfeld[6][6],Spielfeld[6][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");
	printf("7 | %c | %c | %c | %c | %c | %c | %c | %c |\n",Spielfeld[7][0],Spielfeld[7][1],Spielfeld[7][2],Spielfeld[7][3],Spielfeld[7][4],Spielfeld[7][5],Spielfeld[7][6],Spielfeld[7][7]);
	printf("  +---+---+---+---+---+---+---+---+\n");

	//Welcher Spieler ist dran?
	if(ZaehlerA<ZaehlerB)
	{
	printf("Bitte gib die Zeile an: ");
	scanf("%i", &SpielerEingabe1);
	fflush(stdin);
	printf("Bitte gib die Spalte an: ");
	scanf("%i", &SpielerEingabe2);
	fflush(stdin);
	Spielfeld[SpielerEingabe1][SpielerEingabe2] = SpielerA;
	ZaehlerA++;
	}
	else if(ZaehlerA>=ZaehlerB)
	{
		printf("Bitte gib die Zeile an: ");
		scanf("%i", &SpielerEingabe1);
		fflush(stdin);
		printf("Bitte gib die Spalte an: ");
		scanf("%i", &SpielerEingabe2);
		fflush(stdin);
		Spielfeld[SpielerEingabe1][SpielerEingabe2] = SpielerB;
		ZaehlerB++;
	}
	//Spielfeld neu ausgeben
	system("CLS");
	}
	//Solange bis jemand gewonnen hat
	while(GewinnerA != 1 || GewinnerB != 1);
	system("Pause");
	return 0;
}

Ich verlange keine komplette Lösung. Nur Tipps oder gedankenanstösse :D

Danke!

MfG suxido
 
Für den gerade gesetzten Stein wird geprüft, ob ein benachbarter die gleiche Farbe hat. Falls einer gefunden wird, wird dessen Nachbar geprüft usw. ... falls es vier sind hat der Spieler gewonnen. Falls es nicht vier sind, dann muss noch in der anderen Richtung vom Ursprungsstein aus geschaut werden, ob da auch noch welche sind.

Idee genug?
 
Würde auch für jede Richtung eine Funktion schreiben die diese Richtung (horizontal, vertikal, schräg links, schräg rechts) prüft, so grob so (den Code habe ich nicht getestet also vielleicht sind Fehler drin, aber als grobe Idee... ich hoffe ich habe die Grenzen für die while-Schleifen richtig und ohne off-by-one-Fehler :D):

Code:
#define FIELD_X_LENGTH 8

int check_win(int x, int y, char player) {

  /* check if there is a row in any direction */
  if( check_horizontal(x, y, player) ||
      check_vertical(x, y, player) ||
      check_left(x, y, player) ||
      check_right(x, y, player) )
    return 1;
    
  return 0;

}

int check_horizontal(int x, int y, char player) {

  int row_length = 1;
  int px = x + 1;
  
  /* count markers in positive x-direction */
  while(Spielfeld[y][px] == player && px < FIELD_X_LENGTH) {
    row_length++;
    px++;
  }
  
  /* reset position */
  px = x - 1;
  /* count markers in negative x-direction */
  while(Spielfeld[y][px] == player && px >= 0) {
    row_length++;
    px--;
  }
  
  return row_length >= 4 ? 1 : 0;
}
 
Zuletzt bearbeitet: (x/y bei Spielfeld vertauscht.)
Geht sicher noch schöner (z.B. variable Feldgröße etc), aber da mir langweilig war habe ich auch mal eine Version geschrieben (könnte natürlich auch noch andere Fehler haben):

Code:
#include <stdio.h>

#define FIELD_WIDTH 7
#define FIELD_HEIGHT 6

char field[FIELD_WIDTH][FIELD_HEIGHT];

void printField()
{
  int i, j;
  for (i = 1; i <= FIELD_WIDTH; i++)
    printf("%i", i);

  for (j = 0; j < FIELD_HEIGHT; j++)
  {
    for (i = 0; i < FIELD_WIDTH; i++)
      printf("%c", field[i][j]);
    printf("\n");
  }
}

// check if player that has the disc in (col, row)
// has 4 connected discs in direction (x, y)
int checkWin(col, row, x, y)
{
  char player = field[col][row];
  int i;
  int checkX, checkY;
  for (i = 1; i < 4; i++)
  {
    checkX = col + i * x;
    checkY = row + i * y;
    if (checkX < 0 || checkX >= FIELD_WIDTH ||
        checkY < 0 || checkY >= FIELD_HEIGHT)
      return 0;
    if (field[checkX][checkY] != player)
      return 0;
  }
  return 1;
}

int main(int argc, char** argv)
{
  // initialize field
  int i, j;
  for (i = 0; i < FIELD_WIDTH; i++)
    for (j = 0; j < FIELD_HEIGHT; j++)
      field[i][j] = ' ';

  char currentPlayer = 'O';
  char winner = '\0';
  int gameOver = 0;

  while (!gameOver)
  {
    currentPlayer = (currentPlayer == 'X') ? 'O' : 'X';

    printField();

    int col = -1;
    while (!(col > 0 && col <= FIELD_WIDTH && field[col-1][0] == ' '))
    {
      printf("Player %c, choose a column: ", currentPlayer);
      scanf("%i", &col);
    }
    col--; // 0-based index -> 1-based index

    // insert disc
    int row;
    for (row = FIELD_HEIGHT - 1; row >= 0; row--)
    {
      if (field[col][row] == ' ')
      {
        field[col][row] = currentPlayer;
        break;
      }
    }

    // check if player won by checking for 4 connected discs in any direction
    for (i = -1; i <= 1 && !gameOver; i++)
      for (j = -1; j <= 1 && !gameOver; j++)
        if (!(i == 0 && j == 0) && checkWin(col, row, i, j))
        {
          winner = currentPlayer;
          gameOver = 1;
        }

    // check if field is full
    gameOver = 1;
    for (i = 0; i < FIELD_WIDTH; i++)
      if (field[i][0] == ' ')
      {
        gameOver = 0;
        break;
      }
  }

  printField();

  if (winner != '\0')
    printf("Player %c wins!\n", winner);
  else
    printf("No winner!\n");

  return 0;
}
Hierbei wird jeweils nur die Spalte angegeben, in die der Spieler seinen Spielstein ("disc") "einwirft".
 
Zuletzt bearbeitet: (check for full, spoiler tag)

Ähnliche Themen

Zurück
Oben