Mastermind [funktioniert nicht]



  • #include <stdio.h>
    #include <stdlib.h>
    int main()
    
    {
    
       unsigned char vorgabe[4];
       int j,k,i;
       unsigned char eingabe[5];
       srand(time(0));
    
       /////////////////ZUFALL AM ANFANG FESTLEGEN ///////////////////////////////////
       for(j=0;j<4;j++)
       {
          vorgabe[j] = rand()%6+97;
       }
       ////////////////////////////////////////////////////////////////////////////
    
     //  vorgabe[0] = 'a';
     //  vorgabe[1] = 'b';
      // vorgabe[2] = 'c';
      // vorgabe[3] = 'd';
    
       printf("MasterMind v1.0\n");
    
       ////////////////EINGABE VOM BENUTZER///////////////////////////////////////
    
       do
       {
         for(j=0;j<4;j++)
         {
          scanf("%c", &eingabe[j]);
         }
    
         for(j=0;j<4;j++)
         {
          printf("%c", eingabe[j]);
         }
    
         for(k=0;k<4;k++)
         {
            if(eingabe[k]==vorgabe[k])
            {
               printf("*");
            }
            else
            {
               for(i=0;i<4;i++)
               {
                  if(eingabe[i]==vorgabe[k])
                  {
                     printf("+");
                  }
               }
            }
          }
       }while((vorgabe[0] != eingabe[0]) || (vorgabe[1] != eingabe[1]) || (vorgabe[2] != eingabe[2]) || (vorgabe[3] != eingabe[3]));
    
       printf("\nGlueckwunsch, du hast es geschafft!\n");
       ////////////////////////////////////////////////////////////////////////////
    
       //////////////
    
    }
    

    wer nich weiß was mastermind is: http://de.wikipedia.org/wiki/Mastermind

    es is anstatt farben halt mit buchstaben von a - f

    bitte helft mir, ich weiß nicht wo der fehler is, beim kompilierne kommt keinder, aber das programm läuft halt nicht richtig.

    mfg



  • Hallo floriii,

    dein Problem ist der Tastaturpuffer. Nach jeder Eingabe müsstest du ihn
    leeren, sonst liefert ein zweites scanf() ein falsche Zeichen zurück.

    Nach der Eingabe von "a <enter>" befinden sich mindestens das 'a' und '\n'
    im Tastaturpuffer. Das erste scanf() liefert dir 'a' und ein weiteres scanf()
    das Zeichen '\n', was dann zu einem falschen Verhalten deiner Funktion führt.

    Hier mal ein verbesserter Ansatz:

    #include <stdio.h>
    #include <stdlib.h>
    #include <time.h>
    
    static void clearbuffer() { 
        int c;
        while ((c = fgetc(stdin)) != '\n');
    }
    
    static int check_input(unsigned char vor[4], unsigned char ein[4]) {
        unsigned int i, k;
        int ok = 1;
        for(k=0;k<4;k++) {
            if (ein[k] == vor[k]) {
                printf("*");
            } else {
                ok = 0;
                for(i=0;i<4;i++) {
                    if (ein[i] == vor[k]) {
                        printf("+");
                    }
                }
            }
        }
        printf("\n");
        return ok;
    }
    
    int main(){
        unsigned char vorgabe[4];
        int j, ok;
        unsigned char eingabe[4];
        srand(time(0));
    
        /* ZUFALL AM ANFANG FESTLEGEN */
        for(j=0;j<4;j++) {
            vorgabe[j] = rand()%6+97;
        }
    
        for (j=0; j<4; ++j) printf(" %c ", vorgabe[j]);
        printf("\n");
    
        printf("MasterMind v1.0\n");
    
        /* EINGABE VOM BENUTZER */
    
        do {
            for(j=0;j<4;j++) {
                printf("Eingabe %d  : ", j);
                scanf("%c", &eingabe[j]);
                clearbuffer();
            }
    
            for(j=0;j<4;j++) {
                printf("%c", eingabe[j]);
            }
    
            ok = check_input(vorgabe, eingabe);
    
        } while(!ok);
    
        printf("\nGlueckwunsch, du hast es geschafft!\n");
    
        return 0;
    }
    

    Ich habe nur noch den Check in eine Funktion ausgelagert. Dieser
    Check entspricht genau deinem, liefert aber im Sinne des Spieles falsche
    Hilfen.

    Nimm mal folgende Vorgabe: d e d d
    und folgende Eingabe: a d a a
    Dann liefert dein Check folgende Hilfe: +++
    Das "d" ist aber nur einmal in Eingabe enthalten. Richtig wäre: +

    Gruß mcr



  • #include <windows.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <time.h>
    #include <limits.h>
    #include <conio.h>
    
    #define LINELEN 80
    #define ANZAHL_VERSUCHE 12
    #define ANZAHL_BUCHSTABEN 4
    #define POSITION_UND_BUCHSTABE_RICHTIG '*'
    #define BUCHSTABE_RICHTIG '+'
    
    char vorgabe[ANZAHL_BUCHSTABEN+1];
    char eingabe[ANZAHL_BUCHSTABEN+1];
    
    char position_und_buchstabe_richtig[ANZAHL_BUCHSTABEN+1];
    char buchstabe_richtig[ANZAHL_BUCHSTABEN+1];
    
    typedef int bool;
    enum{false, true};
    
    const char* geschafft = "\nGlueckwunsch, du hast es geschafft !";
    const char* looser_msg = "\nAnzahl Versuche abgelaufen.";
    const char* game = "MasterMind v1.01 - Beta ;-) \n";
    
    int start_x = 0, start_y = 3;
    
    /////////////////// POSITION DER Y KOORDINATE ERMITTELN //////////////////// 
    
    int wo_y()
    {
    	CONSOLE_SCREEN_BUFFER_INFO  csbi= {0};
    	GetConsoleScreenBufferInfo( GetStdHandle( STD_OUTPUT_HANDLE ), &csbi );
    	return csbi.dwCursorPosition.Y;
    }
    /////////////////// POSITION DER X KOORDINATE ERMITTELN //////////////////// 
    
    int wo_x()
    {
    	CONSOLE_SCREEN_BUFFER_INFO  csbi= {0};
    	GetConsoleScreenBufferInfo( GetStdHandle( STD_OUTPUT_HANDLE ), &csbi );
    	return csbi.dwCursorPosition.X;
    }
    
    /////////////////// CURSOR AN POSITION XY SETZEN ////////////////////////// 
    
    void geh_xy( int x, int y )
    {
    	COORD pos;
    	pos.X = x;
    	pos.Y = y;
        SetConsoleCursorPosition( GetStdHandle( STD_OUTPUT_HANDLE ), pos );
    }
    
    ////////////////////////////////////////////////////////////////////////////
    
    /////////////////	MACHT DEN EINGABEPUFFER LEER  //////////////////////////
    
    void eingabe_reset()
    {
    	setvbuf( stdin, NULL, _IONBF, 0 );
        setvbuf( stdin, NULL, _IOFBF, BUFSIZ );
    }
    
    ////////////////////////////////////////////////////////////////////////////
    
    ////////////////   MACHT DEN AUSGABEPUFFER LEER  ////////////////////////////
    void ausgabe_reset ()
    {
    	memset( position_und_buchstabe_richtig, 0, ANZAHL_BUCHSTABEN );
    	memset( buchstabe_richtig, 0, ANZAHL_BUCHSTABEN );
    }
    ////////////////////////////////////////////////////////////////////////////
    
    /////////////////	ZUFALL AM ANFANG FESTLEGEN	 ///////////////////////////
    void init ()
    {
    	int i;
    	srand ( time( 0 ) );
    	for ( i = 0; i < ANZAHL_BUCHSTABEN ; i++ )
    		vorgabe[i] = (unsigned char) (rand()%6+97);
    	//vorgabe[i] =  ( 90.0 - 65 ) / RAND_MAX *  rand() + 65;
    }
    ////////////////////////////////////////////////////////////////////////////
    
    ////////////////   EINGABE MIT VORGABE VERGLEICHEN  ////////////////////////
    
    // Ist k == ANZAHL_BUCHSTABEN, wurde alles richtig erraten.
    int vergleich ()
    {	
    	int i, j, k=0, l=0;
    
    	for( i = 0; i < ANZAHL_BUCHSTABEN; i++ )
        {
           if( eingabe[i] == vorgabe[i] )
           {
    		   position_und_buchstabe_richtig[k++] = POSITION_UND_BUCHSTABE_RICHTIG;
    	   }
           else
           {
              if ( strchr( vorgabe, eingabe[i] ) != NULL )
                    buchstabe_richtig[l++] = BUCHSTABE_RICHTIG;
    
           }
    	}  
    	return k; // Ist k == ANZAHL_BUCHSTABEN, wurde alles richtig erraten.
    }
    ///////////////////////////////////////////////////////////////////////////
    
    //////////////// SPIELREGELN ANZEIGEN /////////////////////////////////////
    void regeln ()
    {
    	system("cls");
    	puts("Regeln:");
    	puts("Buchstabe und Position richtig, * ");
    	puts("Buchstabe richtig, an falscher Position, Ausgabe: + ");
    	puts("");
    	getch();
    
    }
    
    /////////////////  INTRO  ////////////////////////////////////////////////
    void intro ()
    {
    // zensiert :D
    }
    ///////////////////////////////////////////////////////////////////////////
    
    //////////////// CURSORPOSITION AUF GÜLTIGKEIT PRÜFEN /////////////////////
    
    bool x_position_gueltig( int x )
    {
    	return x >= 0 && x <= ( ANZAHL_BUCHSTABEN-1 );
    }
    
    /////////////// ENTFERNT DAS ZEILENUMBRUCHZEICHEN //////////////////////////
    
    void weg_mit_dem_doofen_zeilenumbruch(char* buf)
    {
    	if( strchr( buf, '\n' ) )
    		*( strchr( buf, '\n' ) ) = 0;
    
    }
    
    ////////////////////////////////////////////////////////////////////////////
    
    //////////////// BENUTZEREINGABE SPEICHERN/////////////////////////////////
    
    // Gibt im Fehlerfall 1 zurück, sonst 0
    int eingeben ()
    {
    	char linebuf[LINELEN+1]={0};
    	char* so_nicht = "Bitte %d Buchstaben eingeben." ;
    
    	int y = wo_y();
    	int len;
    
    	while(1)
    	{
    		if( NULL == fgets( linebuf, sizeof(linebuf), stdin ))
    			return 1;
    		weg_mit_dem_doofen_zeilenumbruch(linebuf);
    
    		if( ( len = strlen( linebuf )) == ANZAHL_BUCHSTABEN )
    			break;
    
    		geh_xy(0,y);
    		printf( so_nicht, ANZAHL_BUCHSTABEN );
    
    		getch();
    		memset( linebuf, 0, LINELEN );
    		memset( linebuf, ' ', LINELEN );
    
    		geh_xy(0,y);
    		printf(linebuf);
    
    		geh_xy(0,y);
    
    	}
    
    	strcpy( eingabe, linebuf );
    
    	return 0;
    }
    ///////////////////////////////////////////////////////////////////////////
    
    ////////////////  ZEIGT EINE ERFOLGSMELDUNG AN /////////////////////////////////
    
    void glueckwunsch()
    {
    	puts( geschafft );
    }
    
    ///////////////////////////////////////////////////////////////////////////
    
    ////////////////  ZEIGT EINE MISTERFOLGSMELDUNG AN ////////////////////////
    void schade()
    {
    	puts( looser_msg );
    }
    
    ///////////////////////////////////////////////////////////////////////////
    
    ////////////////  ZEIGT DIE AUSWERTUNG DER EINGABE AN ////////////////////
    
    // Das Ergebnis der Funktion vergleich() wird ausgegeben.
    
    void vergleich_anzeige()
    {
    	char buf[ANZAHL_BUCHSTABEN*2+1] = {0};
    	int y = wo_y();
    	memset( buf, 32, ANZAHL_BUCHSTABEN*2 );
    	geh_xy( 0, y-1 );
    	printf(buf);
    	geh_xy( 0, y-1 );
    	printf("%s %s%s\n", eingabe, position_und_buchstabe_richtig, buchstabe_richtig );
    
    }
    
    ///////////////////////////////////////////////////////////////////////////
    
    ////////////////  ZEIGT DIE ZU ERRATENDE VORGABE AN ///////////////////////
    
    void vorgabe_anzeige()
    {
    	int i;
    	char buf[ANZAHL_BUCHSTABEN+1]={0};
    
    	memset( buf, 32, ANZAHL_BUCHSTABEN );
    
    	for ( i=0; i<8; i++ ) // Ein bisschen Show muss sein ;)
    	{
    		Sleep(200);
    		geh_xy( start_x, start_y );
    		printf( buf );
    		Sleep(200);
    		geh_xy( start_x, start_y );
    		printf( vorgabe );
    	}
    
    	geh_xy( start_x, start_y + 15 );
    }
    
    void menue()
    {
    	int c;
    
    	while( c != '1' )
    	{
    		system("cls");
    
    		puts(game);
    		printf("1 Start.\n");
    		printf("2 Spielregeln.\n");
    
    		c = getch();
    		if ( c == '2' )
    			regeln();
    
    	}
    
    	system("cls");
    	intro();
    }
    
    ///////////////////////////////////////////////////////////////////////////
    
    int main ()
    {
    	int i, ret;
    
    	char buf[ANZAHL_BUCHSTABEN+1]={0};
    	memset( buf, '?', ANZAHL_BUCHSTABEN );
    
    	init();
    	menue();
    
    	puts(game);
    
    	geh_xy( start_x, start_y );
    	puts( buf );
    	puts("");
    
      	for( i=0; i<ANZAHL_VERSUCHE; i++ )
    	{
    		if( eingeben () )
    			return 1;
    
    		ret = vergleich();
    		vergleich_anzeige();
    
    		if( ret == ANZAHL_BUCHSTABEN )
    		{
    			glueckwunsch();
    			break;
    		}
    
    		eingabe_reset();
    		ausgabe_reset();
    	}
    
    	if ( i == ANZAHL_VERSUCHE )
    		schade(); 
    
        vorgabe_anzeige();
    	getch();
    	return 0;
    
    }
    

Anmelden zum Antworten