Tic Tac Toe AI error - c

char checkwinner(char ttt[][3]) {
char winner = 0;
for (int p = 0; winner == 0 && p < 2; p++) {
char XO = p == 0 ? 'x' : 'o';
for (int i = 0; winner == 0 && i < 3; i++) {
if (ttt[i][0] == XO && ttt[i][1] == XO && ttt[i][2] == XO)
winner = XO;
else
if (ttt[0][i] == XO && ttt[1][i] == XO && ttt[2][i] == XO)
winner = XO;
}
if (winner == 0 && ttt[0][0] == XO && ttt[1][1] == XO && ttt[2][2] == XO)
winner = XO;
else
if (winner == 0 && ttt[0][2] == XO && ttt[1][1] == XO && ttt[2][0] == XO)
winner = XO;
}
return winner;
}
int main (void) {
char b[3][3] = {{'1', '2', '3'},
{'4', '5', '6'},
{'7', '8', '9'}};
int turn = 0, i, j, loc, type, counter = 0;
char XO, AL;
char theChar = 'A';
char junk ='A';
printf("Type in 1 to play with AL, or 2 to play with another human\n");
scanf("%d", &type);
while (turn <= 9) {
char winner = checkwinner(b);
if (winner == 'x' || winner == 'o') {
printf("%c has won! You get 100 million DOGECOINS! Just enter your debt card information to our website, as well as your checking account and social security number. Go to www.THIS_IS_NOT_A_SCAM.com to get your dogecoins today!\n", winner);
return (0);
} else
if (((b[0][0] == 'x') || (b[0][0] == 'o'))
&& ((b[0][1] == 'x') || (b[0][1] == 'o'))
&& ((b[0][2] == 'x') || (b[0][2] == 'o'))
&& ((b[1][0] == 'x') || (b[1][0] == 'o'))
&& ((b[1][1] == 'x') || (b[1][1] == 'o'))
&& ((b[1][2] == 'x') || (b[1][2] == 'o'))
&& ((b[2][0] == 'x') || (b[2][0] == 'o'))
&& ((b[2][1] == 'x') || (b[2][1] == 'o'))
&& ((b[2][2] == 'x') || (b[2][2] == 'o'))) {
printf("This is a tie.\n");
return (0);
} //<---- missing brace!
if (type == 1) {
counter = counter + 1;
if (counter == 1) { XO = 'x'; }
if (counter == 2) { XO = 'o'; }
if (counter == 3) { XO = 'x'; }
if (counter == 4) { XO = 'o'; }
if (counter == 5) { XO = 'x'; }
if (counter == 6) { XO = 'o'; }
if (counter == 7) { XO = 'x'; }
if (counter == 8) { XO = 'o'; }
if (counter == 9) { XO = 'x'; }
}
if (type == 2) {
XO = 'x';
AL = 'o';
for (i = 0; i < 3; i++) {
for (j = 0; j < 3; j++) {
b[i][j] = AL;
printArray(b);
}
}
}
theChar = getchar();
putchar(theChar);
printf("Enter number: ");
scanf("%d", &loc);
j = (loc - 1) % 3;
i = (loc - 1) / 3;
if ((b[i][j] == 'x') || (b[i][j] == 'o')) {
printf("That spot has been taken!\n");
return (0);
}
putchar('\n');
junk = getchar();
b[i][j] = XO;
printArray(b);
}
}
void printArray(char thearray[3][3]) {
int i, j;
for (i = 0; i < 3; i++) {
for (j = 0; j < 3; j++) {
printf("%c ", thearray[i][j]);
}
printf("\n");
}
}
Right now I'm trying to finish the AI mode. Rather than just going and finding the first empty space and printing a single 'o' my game prints 9 boards like this:
o 2 3
4 5 6
7 8 9
o o 3
4 5 6
7 8 9
o o o
4 5 6
7 8 9
o o o
o 5 6
7 8 9
o o o
o o 6
7 8 9
o o o
o o o
7 8 9
o o o
o o o
o 8 9
o o o
o o o
o o 9
o o o
o o o
o o o
How do I get the game to stop after printing one 'o', and then letting 'x' pick a move? All help is appreciated.

Your code to find the place for AL to play is incorrect:
if (type == 2) {
XO = 'x';
AL = 'o';
for (i = 0; i < 3; i++) {
for (j = 0; j < 3; j++) {
b[i][j] = AL;
printArray(b);
}
}
}
You just play every spot on the grid and print it!
Try this instead:
if (type == 2) {
XO = 'x';
AL = 'o';
for (i = 0; i < 3; i++) {
for (j = 0; j < 3; j++) {
if (b[i][j] != 'x' && b[i][j] != 'o') {
b[i][j] = AL;
i = j = 2; /* ugly way to exit the nested loops */
}
}
}
printArray(b);
}
But this gaming strategy will be easy to beat!
Also you forget to increment turn, but if you did, you could replace the tedious test for a tie with a simple if (turn == 9).
EDIT: exiting from this nested loop requires more logic... it is better to move the AL game play to a separate function. Furthermore, your logic is flawed: you let AL play if type is 2 instead of 1...
Here is a simplified and corrected version that can play both sides:
#include <stdio.h>
char checkwinner(char b[3][3]) {
for (int i = 0; i < 3; i++) {
if (b[i][0] == b[i][1] && b[i][1] == b[i][2])
return b[i][0];
if (b[0][i] == b[1][i] && b[1][i] == b[2][i])
return b[0][i];
}
if ((b[0][0] == b[1][1] && b[1][1] == b[2][2])
|| (b[0][2] == b[1][1] && b[1][1] == b[2][0])) {
return b[1][1];
}
return 0;
}
void printArray(char b[3][3]) {
for (int i = 0; i < 3; i++) {
printf("%c %c %c\n", b[i][0], b[i][1], b[i][2]);
}
printf("\n");
}
void playAl(char b[3][3], char AL) {
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
if (b[i][j] != 'x' && b[i][j] != 'o') {
b[i][j] = AL;
return;
}
}
}
}
int main (void) {
char board[3][3] = {{'1', '2', '3'},
{'4', '5', '6'},
{'7', '8', '9'}};
int turn, i, j, loc, type;
printf("What does AL play? (0:none, 1:x, 2:o, 3:both) ");
scanf("%d", &type);
for (turn = 0;; turn++) {
printArray(board);
char winner = checkwinner(board);
if (winner == 'x' || winner == 'o') {
printf("%c has won! Game over\n", winner);
return 0;
}
if (turn == 9) {
printf("This is a tie.\n");
return 0;
}
char XO = "xo"[turn % 2];
if (type & (1 << (turn % 2))) {
/* AL's turn to play */
playAl(board, XO);
continue;
}
for (;;) {
printf("Enter number: ");
if (scanf("%d", &loc) != 1)
return 1;
j = (loc - 1) % 3;
i = (loc - 1) / 3 % 3;
if (board[i][j] != 'x' && board[i][j] != 'o')
break;
printf("This spot is already taken!, try again\n");
}
board[i][j] = XO;
}
}

Related

How do I add power ups to my space invader game in C language like, double shooting, adding firing speed?

I'm having trouble with adding power ups. I don't know where to put it. I'm a first year college; can somebody help?
This is what I did. I want to add power ups in this game where whenever I destroy enemy, it drops power ups like firing speed and double shooting.
I don't know what to put inside to have the enemy drop some power up.
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <windows.h>
int main()
{
int sizey = 23;
int sizex = 40;
int x, y, yi;
char world[sizey][sizex];
char player = 'A';
char playerLaser = '^';
char enemy = 'M';
char enemyShielded = 'O';
char enemyLaser = 'U';
char explosion = 'X';
int score = 0;
int victory = 1;
int laserReady = 1;
int enemyReady = 0;
srand(time(NULL));
/*welcome screen*/
printf("\n \n Welcome soldier! \n \n \n \n");
Sleep(1000);
printf(" Brave the COMMAND PROMPT INVADERS and come back a hero. \n \n \n \n");
Sleep(2500);
printf(" Your operating system is depending upon you. \n \n \n \n");
Sleep(2500);
printf(" Good luck.");
Sleep(1000);
printf("\n \n \n \n Press any key to start.");
getch();
/*initialise world*/
int totalEnemies = 0;
for (x = 0; x < sizex; x ++) {
for (y = 0; y < sizey; y ++) {
if ((y+1) % 2 == 0 && y < 7 && x > 4
&& x < sizex - 5 && x % 2 ==0) {
world[y][x] = enemy;
totalEnemies ++;
}
else if ((y+1) % 2 == 0 && y >= 7 && y < 9 && x > 4
&& x < sizex - 5 && x % 2 ==0){
world[y][x] = enemyShielded;
totalEnemies = totalEnemies + 2;
}
else {
world[y][x] = ' ';
}
}
}
world[sizey - 1][sizex / 2] = player;
int i = 1;
char direction = 'l';
char keyPress;
int currentEnemies = totalEnemies;
while(currentEnemies > 0 && victory) {
int drop = 0;
int enemySpeed = 1 + 10 * currentEnemies / totalEnemies;
laserReady ++;
/*display world*/
system("cls");
printf(" SCORE: %d", score);
printf("\n");
for (y = 0; y < sizey; y ++) {
printf("|");
for (x = 0; x < sizex; x ++) {
printf("%c",world[y][x]);
}
printf("|");
printf("\n");
}
/*laser time*/
for (x = 0; x < sizex; x ++) {
for (y = sizey-1; y >= 0; y --) {
if (i%2 == 0 && world[y][x] == enemyLaser
&& (world[y+1][x] != enemy & world[y+1][x] != enemyShielded)){
world[y+1][x] = enemyLaser;
world[y][x] = ' ';
}
else if (i%2 == 0 && world[y][x] == enemyLaser
&& (world[y+1][x] == enemy | world[y+1][x] == enemyShielded)){
world[y][x] = ' ';
}
}
}
for (x = 0; x < sizex; x ++) {
for (y = 0; y < sizey; y ++) {
if ((i % 5) == 0 && (world[y][x] == enemyShielded
| world[y][x] == enemy) && (rand() % 15) > 13
&& world[y+1][x] != playerLaser) {
for (yi = y+1; yi < sizey; yi ++) {
if (world[yi][x] == enemy
| world[yi][x] == enemyShielded) {
enemyReady = 0;
break;
}
enemyReady = 1;
}
if (enemyReady) {
world[y+1][x] = enemyLaser;
}
}
if (world[y][x] == playerLaser && world[y-1][x] == enemy) {
world[y][x] = ' ';
world[y-1][x] = explosion;
currentEnemies --;
score = score + 50;
}
else if (world[y][x] == playerLaser
&& world[y-1][x] == enemyShielded) {
world[y][x] = ' ';
world[y-1][x] = enemy;
currentEnemies --;
score = score + 50;
}
else if (world[y][x] == playerLaser
&& world[y-1][x] == enemyLaser) {
world[y][x] = ' ';
}
else if (world[y][x] == explosion) {
world[y][x] = ' ';
}
else if ((i+1) % 2 == 0 && world[y][x] == enemyLaser
&& world[y+1][x] == player) {
world[y+1][x] = explosion;
world[y][x] = ' ';
victory = 0;
}
else if (world[y][x] == playerLaser
&& world[y-1][x] != enemyLaser) {
world[y][x] = ' ';
world[y-1][x] = playerLaser;
}
}
}
/*update enemy direction*/
for (y = 0; y < sizey; y ++) {
if (world[y][0] == enemy) {
direction = 'r';
drop = 1;
break;
}
if (world[y][sizex-1] == enemy){
direction = 'l';
drop = 1;
break;
}
}
/*update board*/
if (i % enemySpeed == 0) {
if (direction == 'l') {
for (x = 0; x < sizex - 1; x ++) {
for (y = 0; y < sizey; y ++) {
if (drop && (world[y-1][x+1] == enemy
|| world[y-1][x+1] == enemyShielded)){
world[y][x] = world[y-1][x+1];
world[y-1][x+1] = ' ';
}
else if (!drop && (world[y][x+1] == enemy
|| world[y][x+1] == enemyShielded)) {
world[y][x] = world[y][x+1];
world[y][x+1] = ' ';
}
}
}
}
else {
for (x = sizex; x > 0; x --) {
for (y = 0; y < sizey; y ++) {
if (drop && (world[y-1][x-1] == enemy
|| world[y-1][x-1] == enemyShielded)) {
world[y][x] = world[y-1][x-1];
world[y-1][x-1] = ' ';
}
else if (!drop && (world[y][x-1] == enemy
|| world[y][x-1] == enemyShielded)) {
world[y][x] = world[y][x-1];
world[y][x-1] = ' ';
}
}
}
}
for (x = 0; x < sizex; x ++) {
if (world[sizey - 1][x] == enemy) {
victory = 0;
}
}
}
/*control player*/
if(kbhit()){
keyPress = getch();
}
else {
keyPress = ' ';
}
if (keyPress == 'a') {
for (x = 0; x < sizex; x = x+1) {
if ( world[sizey-1][x+1] == player) {
world[sizey-1][x] = player;
world[sizey-1][x+1] = ' ';
}
}
}
if (keyPress == 'd') {
for (x = sizex - 1; x > 0; x = x-1) {
if ( world[sizey-1][x-1] == player) {
world[sizey-1][x] = player;
world[sizey-1][x-1] = ' ';
}
}
}
if (keyPress == 'm' && laserReady > 2) {
for (x = 0; x < sizex; x = x+1) {
if ( world[sizey-1][x] == player) {
world[sizey - 2][x] = playerLaser;
laserReady = 0;
}
}
}
i ++;
Sleep(50);
}
system("cls");
printf(" SCORE: %d", score);
printf("\n");
for (y = 0; y < sizey; y ++) {
printf("|");
for (x = 0; x < sizex; x ++) {
printf("%c",world[y][x]);
}
printf("|");
printf("\n");
}
Sleep(1000);
system("cls");
if (victory != 0) {
printf("\n \n \n \n \n \n CONGRATULATIONS! \n \n \n \n \n");
Sleep(1000);
printf("\n \n Score: %d", score);
Sleep(1000);
int bonus = totalEnemies*20 - i;
printf("\n \n Bonus: %d", bonus);
Sleep(1000);
printf("\n \n Total Score: %d", score + bonus);
printf("\n \n \n \n Well done");
Sleep(1000);
printf(", Hero.");
Sleep(1000);
getch();
}
else {
printf("\n \n \n \n \n \n You have failed.");
Sleep(1000);
printf("\n \n \n \n \n \n Windows is doomed.");
Sleep(1000);
printf("\n \n Final Score: %d", score);
getch();
}
}

Movement for game character doesn't work at all

Here is the .c code from start to finish. I suspect it's an order of operations issue or something else.
The code is supposed to have a title screen where you can exit or play. If you hit play it renders a new char array in which you can move either left, right, or down (a/d/s). You get points for going down a row each time as well as going over 'P' spots on the array.
Once you hit y-coordinate 202 on the array as well as have positive points, you win and it renders a congrats char array. If you go negative in points (by hitting the '#' paces or the 'L' wall that goes down a row every 1/2 second) then you will lose and be told you lost in a new char array as well as be asked if you want to exit or play again.
And as mentioned before, the movement for the 'L's and the play character 'O' simply doesn't move.
#include <stdlib.h>
#include <stdio.h>
#include <time.h>
#include <fcntl.h>
#include <unistd.h>
char quickchar(float delay);
void render();
void titleRender();
void renderLoss();
void renderWin();
int score();
char titlescreen[20][59] = { };
char diffdiff[20][46] = {
(Grid removed due to char limit)
};
char gameover[20][50] = {
(Grid removed due to char limit)
};
char gameboard[203][26] = {
(Grid removed due to char limit)
};
int playerx;
int playery;
int pts;
void entryRender();
void gameRender();
int main() {
int input;
char replay;
int lx;
int ly;
char walkin;
int gaming;
char titlechoice;
int diff;
int running;
lx = 0;
ly = 0;
running = 1;
playerx = 13;
playery = 5;
pts = 25;
gaming = 0;
while (gaming == 0) {
titleRender();
printf("\033[1;32m");
printf("\nPress 'p' to play or 'x' to exit!");
printf("\033[0m");
scanf(" %c", &titlechoice);
if (titlechoice == 'p') {
gaming += 4;
}
if (titlechoice == 'x') {
return 0;
}
}
while (gaming == 4) {
system("stty -echo raw");
render();
printf("\033[1;35m");
printf("Choose a direction: s/Down, a/Left, d/Right.\n\r");
printf("\033[0m");
walkin = quickchar(0.5);
scanf("%c", &walkin);
//obj behaviour
if (walkin == 's' &&
gameboard[playery +1][playerx] != '#' &&
gameboard[playery + 1][playerx] != '+' &&
gameboard[playery + 1][playerx] != '|' &&
gameboard[playery + 1][playerx] != '-') {
playery++;
pts += 5;
if (gameboard[playery + 1][playerx] == '#') {
pts -= 25;
}
if (gameboard[playery + 1][playerx] == 'P') {
printf("Points increased!\n\r");
pts += 50;
gameboard[playery + 1][playerx] = '_';
}
}
else if (walkin == 'a' &&
gameboard[playery][playerx - 1] != '#' &&
gameboard[playery][playerx - 1] != '+' &&
gameboard[playery][playerx - 1] != '|' &&
gameboard[playery][playerx - 1] != '-') {
playerx--;
if (gameboard[playery][playerx - 1] == '#') {
pts -= 25;
}
if (gameboard[playery][playerx - 1] == 'P') {
printf("Points increased!\n\r");
pts += 50;
gameboard[playery][playerx - 1] = '_';
}
}
else if (walkin == 'd' &&
gameboard[playery][playerx + 1] != '#' &&
gameboard[playery][playerx + 1] != '+' &&
gameboard[playery][playerx + 1] != '|' &&
gameboard[playery][playerx + 1] != '-') {
playerx++;
if (gameboard[playery][playerx + 1] == '#') {
pts -= 25;
}
if (gameboard[playery + 1][playerx] == 'P) {
printf("Points increased!\n\r");
pts += 50;
gameboard[playery][playerx + 1] = '_';
}
}
if (walkin == 'a' || walkin == 's' || walkin == 'd' ||
walkin != 'a' || walkin != ' ' || walkin != 'd' ) {
for (ly = 0; ly = 202; ly++) {
for (lx = 1; lx = 25; lx++) {
gameboard[ly][lx] = 'L';
}
}
}
if (pts <= 0) {
system("clear");
renderLoss();
scanf("%c", replay);
if (replay == 'Y') {
gaming = 3;
}
if (replay == 'N') {
gaming = 5;
}
}
if (playery == 202) {
renderWin();
printf("");
printf("Congrats! You got a score of %d !", pts);
printf("");
scanf("%c", &replay);
if (replay == 'Y') {
gaming = 4;
}
if (replay == 'N') {
gaming = 5;
}
}
//player postion == 203y, then congrta screen
//ask player to set gaming to 4(replay) or none (exit program)
}
system("stty echo -raw");
return 0;
}
void render() {
int y,x,k;
system("clear");
printf("\033[01;33m");
printf("||POINTS: %d||\r\n", pts);
printf("\033[0m");
for (y = 0; y < 203; y++) {
for (x = 0; x < 26; x++) {
if (y == playery && x == playerx) {
printf("\033[0;32m");
printf("O");
printf("\033[0m");
}
else {
printf("\033[1;36m");
printf("%c", gameboard[y][x]);
printf("\033[0m");
}
}
printf("\r\n");
}
}
void titleRender() {
int y, x;
system("clear");
for (y = 0; y < 20; y++) {
for (x = 0; x < 59; x++) {
printf("\033[0;32m");
printf(" %c", titlescreen[y][x]);
printf("\033[0m");
}
printf("\r\n");
}
}
void renderLoss() {
int y, x;
system("clear");
for (y = 0; y < 26; y++) {
for (x = 0; x < 50; x++) {
printf("\033[0;31m");
printf(" %c", gameover[y][x]);
printf("\033[0m");
}
printf("\r\n");
}
}
void renderWin() {
int y, x;
system("clear");
for (y = 0; y < 20; y++) {
for (x = 0; x < 46; x++) {
printf("\033[0;33m");
printf(" %c", diffdiff);
printf("\033[0m");
}
printf("\r\n");
}
}
char quickchar(float delay) {
int flags;
char c;
usleep((int)(delay*1000000));
flags = fcntl(0, F_GETFL, 0);
fcntl(0, F_SETFL, flags | O_NONBLOCK);
c = getchar();
fcntl(0, F_SETFL, flags ^ O_NONBLOCK);
return c;
}

SetConsoleCursorPosition : Getting black rows in console upon use

Following my previous question about making a snake program more fluid, I went and tried ANSI escape sequences and console functions to put back the text cursor on the top left corner.
I want to get the cursor on the top left corner of the screen, but while it does so I get black stripes across the screen every other line.
I am working in a windows environment making this program for the windows console.
Here is the painting function :
void paint(int tab[28][120], int ligneMax, int colonneMax, HANDLE hconsole)
{
//system("cls");
//printf("\033[1;1H");
COORD destCoord;
destCoord.X = 0;
destCoord.Y = 0;
SetConsoleCursorPosition(hconsole, destCoord);
for (int i = 0; i < ligneMax; i++)
{
for (int j = 0; j < colonneMax; j++)
{
printf("%c", tab[i][j]);
}
printf("\n");
}
}
I tried putting the escape code and console function in the main right before calling the paint function but I got the same results.
here is the whole program if someone wants to test :
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <Windows.h>
void paint(int tab[28][120], int ligneMax, int colonneMax, HANDLE hconsole)
{
//system("cls");
//printf("\033[1;1H");
COORD destCoord;
destCoord.X = 0;
destCoord.Y = 0;
SetConsoleCursorPosition(hconsole, destCoord);
for (int i = 0; i < ligneMax; i++)
{
for (int j = 0; j < colonneMax; j++)
{
printf("%c", tab[i][j]);
}
printf("\n");
}
}
void create(int tab[28][120], int Nbligne, int Nbcolonne,
int randligne, int randcols)
{
for (int i = 0; i < Nbligne; i++)
{
for (int j = 0; j < Nbcolonne; j++)
{
tab[i][j] = ' ';
if (i == 0 || i == Nbligne - 1)
tab[i][j] = 205;
if (j == 0 || j == Nbcolonne - 1)
tab[i][j] = 186;
if (i == 0 && j == 0)
tab[i][j] = 201;
if (i == 0 && j == Nbcolonne - 1)
tab[i][j] = 187;
if (i == Nbligne - 1 && j == 0)
tab[i][j] = 200;
if (i == Nbligne - 1 && j == Nbcolonne - 1)
tab[i][j] = 188;
if (i == 14 && j == 60)
tab[i][j] = 219;
if (i == 14 && j == 59)
tab[i][j] = 79;
if (i == 14 && j == 58)
tab[i][j] = 35;
if (i == randligne && j == randcols)
tab[i][j] = 176;
}
}
}
void destroyTail(int tab[28][120], int Nbligne, int Nbcolonne)
{
for (int i = 0; i < Nbligne; i++)
{
for (int j = 0; j < Nbcolonne; j++)
{
if (tab[i][j] == 35)
{
tab[i][j] = ' ';
if (tab[i][j + 1] == 79)
tab[i][j + 1] = 35;
else if (tab[i][j - 1] == 79)
tab[i][j - 1] = 35;
else if (tab[i + 1][j] == 79)
tab[i + 1][j] = 35;
else if (tab[i - 1][j] == 79)
tab[i - 1][j] = 35;
goto stop;
}
}
}
stop: NULL;
}
void translate(int tab[28][120], char direction, int Nbligne, int Nbcolonne)
{
for (int i = 0; i < Nbligne; i++)
{
for (int j = 0; j < Nbcolonne; j++)
{
if (tab[i][j] == 219)
{
if (direction == 'R')
{
tab[i][j] = 79;
tab[i][j + 1] = 219;
}
if (direction == 'D')
{
tab[i][j] = 79;
tab[i + 1][j] = 219;
}
if (direction == 'L')
{
tab[i][j] = 79;
tab[i][j - 1] = 219;
}
if (direction == 'U')
{
tab[i][j] = 79;
tab[i - 1][j] = 219;
}
goto stop;
}
}
}
stop: NULL;
}
int checkExpand(int tab[28][120], int Nbligne, int Nbcolonne, char direction)
{
for (int i = 0; i < Nbligne; i++)
{
for (int j = 0; j < Nbcolonne; j++)
{
if ((direction == 'R' && tab[i][j] == 219 && tab[i][j + 1] == 176) ||
(direction == 'L' && tab[i][j] == 219 && tab[i][j - 1] == 176) ||
(direction == 'U' && tab[i][j] == 219 && tab[i - 1][j] == 176) ||
(direction == 'D' && tab[i][j] == 219 && tab[i + 1][j] == 176))
return 1;
}
}
return 0;
}
int checkDeath(int tab[28][120], int Nbligne, int Nbcolonne, char direction)
{
for (int i = 0; i < Nbligne; i++)
{
for (int j = 0; j < Nbcolonne; j++)
{
if ((direction == 'R' && tab[i][j] == 219 && (tab[i][j + 1] == 186 || tab[i][j + 1] == 79)) ||
(direction == 'L' && tab[i][j] == 219 && (tab[i][j - 1] == 186 || tab[i][j - 1] == 79)) ||
(direction == 'U' && tab[i][j] == 219 && (tab[i - 1][j] == 205 || tab[i - 1][j] == 79)) ||
(direction == 'D' && tab[i][j] == 219 && (tab[i + 1][j] == 205 || tab[i + 1][j] == 79)))
return 1;
}
}
return 0;
}
int main()
{
HANDLE hConsole;
hConsole = GetStdHandle(STD_OUTPUT_HANDLE);
SetConsoleTextAttribute(hConsole, 241);
int tab[28][120];
int randligne = rand() % 26 + 1;
int randcols = rand() % 118 + 1;
create(tab, 28, 120, randligne, randcols);
paint(tab, 28, 120, hConsole);
char i = '1';
char direction = 'R';
int eaten = 0;
int expand = 0;
int death = 0;
while(i != 'k')
{
if (kbhit())
i = getch();
switch(i) {
case 'z':
if (direction != 'D')
direction = 'U';
break;
case 's':
if (direction != 'U')
direction = 'D';
break;
case 'd':
if (direction != 'L')
direction = 'R';
break;
case 'q':
if (direction != 'R')
direction = 'L';
break;
}
randligne = rand() % 26 + 1;
randcols = rand() % 118 + 1;
death = checkDeath(tab, 28, 120, direction);
if (death == 1)
break;
translate(tab, direction, 28, 120);
expand = checkExpand(tab, 28, 120, direction);
if (expand == 0)
destroyTail(tab, 28, 120);
else
{
while (tab[randligne][randcols] != ' ')
{
randligne = rand() % 26 + 1;
randcols = rand() % 118 + 1;
}
tab[randligne][randcols] = 176;
eaten++;
}
printf("Number of biscuits eaten : %d ; direction : %c ; expand : %d", eaten, direction, expand);
paint(tab, 28, 120, hConsole);
Sleep(100);
}
while(i != 'k')
{
if (kbhit())
i = getch();
}
}
Too much code to take in quickly. If you have Windows console ouput for the snake, can't you simply printf the next line and leave it at that?
If you want to hide the cursor (instead of trying to park it out of sight) you can make it invisible by calling SetConsoleCursorInfo and the struct passed is shown here.

Struggling programming TicTacToe in C

I'm new to C and programming and I tried to code a simple TicTacToe game. I new that I defintaly did many dumb things.
So I have a main .c file and two header files, which I will post here:
main.c:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "game.h"
#include "random.h"
#define NAMELENGTH 20
int main(void) {
char names[2][NAMELENGTH];
// field positions
char field[9];
int winner = -2;
getnames(names);
printf("\n\n");
initField(field);
// set field positions to 'empty'
char actualPlayer = (char)(get_random_number()*10.0) % 2;
while (1) {
drawField(field);
turn(actualPlayer, names, field);
winner = isWinner(actualPlayer, field);
drawField(field);
if (winner >= 0) {
printwinner(winner, names);
return 0;
}
else if (winner == -1) {
printDrawGame(names);
return 0;
}
actualPlayer = (actualPlayer + 1) % 2;
system("cls");
}
return 0;
}
game.h:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define NAMELENGTH 20
#pragma warning(disable:4996)
void drawField(char *field) {
printf("________________________\n");
printf("| | | |\n");
printf("| %c | %c | %c |\n", field[1], field[2], field[3]);
printf("|_______|_______|______|\n");
printf("| | | |\n");
printf("| %c | %c | %c |\n", field[4], field[5], field[6]);
printf("|_______|_______|______|\n");
printf("| | | |\n");
printf("| %c | %c | %c |\n", field[7], field[8], field[9]);
printf("|_______|_______|______|\n");
}
void getnames(char nameField[][NAMELENGTH]) {
printf("Name of the first player: ");
scanf("%s", &nameField[0]);
printf("Name of the second player: ");
scanf("%s", &nameField[1]);
}
void initField(char *field) {
for (int i = 1; i < 10; i++)
{
field[i] = i+48;
}
}
void turn(char actualPlayer, char names[][NAMELENGTH], char *field) {
char symbol = ' ';
int k;
int m;
if (actualPlayer == 1)
{
do {
printf("\nIts Player %s's turn.", names[0]);
char symbol = 'X';
printf("\nNumber of the field which you want to put your symbol in: ");
scanf("%i", &k);
if (field[k] == 'X' || field[k] == 'O')
{
printf("\nField is already occupied!");
k = 10;
}
} while (k < 1 || k > 9);
field[k] = 'X';
}
else {
do {
printf("\nIts Player %s's turn.", names[1]);
char symbol = 'O';
printf("\nNumber of the field which you want to put your symbol in: ");
scanf("%i", &m);
if (field[m] == 'X' || field[m] == 'O')
{
printf("\nField is already occupied!");
m = 10;
}
} while (m < 1 || m > 9);
field[m] = 'X';
}
}
int isWinner(char actualPlayer, char *field) {
int w = 2;
if (((field[1] = 'O') && (field[2] = '0') && (field[3] = '0')) || (field[4] = '0') && (field[5] = '0') && (field[6] = '0') || (field[7] = '0') && (field[8] = '0') && (field[9] = '0') || (field[1] = '0') && (field[5] = '0') && (field[9] = '0') || (field[3] = '0') && (field[5] = '0') && (field[7] = '0') || (field[1] = '0') && (field[4] = '0') && (field[7] = '0') || (field[2] = '0') && (field[5] = '0') && (field[8] = '0') || (field[3] = '0') && (field[6] = '0') && (field[9] = '0'))
{
int w = 1;
}
if (((field[1] = 'X') && (field[2] = 'X') && (field[3] = 'X')) || (field[4] = 'X') && (field[5] = 'X') && (field[6] = 'X') || (field[7] = 'X') && (field[8] = 'X') && (field[9] = 'X') || (field[1] = 'X') && (field[5] = 'X') && (field[9] = 'X') || (field[3] = 'X') && (field[5] = 'X') && (field[7] = 'X') || (field[1] = 'X') && (field[4] = 'X') && (field[7] = 'X') || (field[2] = 'X') && (field[5] = 'X') && (field[8] = 'X') || (field[3] = 'X') && (field[6] = 'X') && (field[9] = 'X'))
{
int w = 0;
}
else
{
int w = -1;
}
return w;
}
void printwinner(char winnerNumber, char names[][NAMELENGTH]) {
if (winnerNumber == 0)
{
printf("Player %s won!", names[0]);
system("exit");
}
else if (winnerNumber == 1)
{
printf("Player %s won!", names[1]);
system("exit");
}
}
void printDrawGame(char names[][NAMELENGTH]) {
printf("Draw!");
system("exit");
}
and random.h:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
static int _initialized;
void init() {
srand(time(NULL));
_initialized = 1;
}
double get_random_number() {
init();
if (!_initialized)
printf("Warning: init() should be called first!\n");
double random;
random = (double)rand() / ((double)(RAND_MAX)+1);
return random;
}
So the Program itself runs till I type in which field I want to put in the symbol. I get a weird error ("Stack around the variable 'field' was corrupted.") and also the random function doesnt work like I want. Would be happy and thankful for you help guys :)
You declared field to be an array of 9 elements. The indices will be 0 to 8. In game.h you have a function initField in which you do:
for (int i = 1; i < 10; i++)
{
field[i] = i+48;
}
This will produce indices 1 to 9, which steps out of bounds for the array.
You reinitialize the random number generator each time it is called. You pseudo random values will not be very random I'm afraid.
Fix it this way:
static int _initialized;
double get_random_number() {
if (!_initialized) {
srand(time(NULL));
_initialized = 1;
}
return = (double)rand() / ((double)(RAND_MAX)+1);
}
You should not write code in header files. Declarations belong in header files, code belongs in source files with the extension .c.

Function and loop trouble in C

This program is expecting the user to input a 7-digit number (except 1 and 0), and any digit has a corresponding set of letters
(2=ABC, 3=DEF, 4=GHI, 5=JKL, 6=MNO, 7=PRS, 8=TUV, 9=XYZ, as found on phones in the USA). Finally, it should output all 2187 possible sequences of letters.
ex: input 2345678
output should be ADGJMPT ADGJMPU ADGJMPV ADGJMRT ADGJMRU ADGJMRV ADGJMST..........CFILOSV
but my output always is AAAAAAA AAAAAAB AAAAAAC..........CCCCCCC
(I also have trouble in checking number. I first set a loop and array, if (che[1] != 1 && che[0] != 1) break; but sometimes it doesn't break.)
Can you explain what's wrong?
#include<stdio.h>
int main(){
int che[50] = { 0 };
int a, b, c, d, e, f, g, i, r, q, number, check;
char word2[7];
char word1[8][3] = {
{ 'A', 'B', 'C' },
{ 'D', 'E', 'F' },
{ 'G', 'H', 'I' },
{ 'J', 'K', 'L' },
{ 'M', 'N', 'O' },
{ 'P', 'R', 'S' },
{ 'T', 'U', 'V' },
{ 'W', 'X', 'Y' } };
while (1)
{
printf("Enter seven digit(except 0 and 1):");
scanf("%d", &number);
check = number;
for (; number != 0; number /= 10)
{
q = number % 10;
che[q] = 1;
}
if (che[1] != 1 && che[0] != 1) break;
}
number = check;
for (i = 6; number == 0; i--)
{
r = number % 10;
if (r == 2){ word2[i] = 0; }
if (r == 3){ word2[i] = 1; }
if (r == 4){ word2[i] = 2; }
if (r == 5){ word2[i] = 3; }
if (r == 6){ word2[i] = 4; }
if (r == 7){ word2[i] = 5; }
if (r == 8){ word2[i] = 6; }
if (r == 9){ word2[i] = 7; }
number /= 10;
}
for (a = 0; a < 3; a++){
for (b = 0; b < 3; b++){
for (c = 0; c < 3; c++){
for (d = 0; d < 3; d++){
for (e = 0; e < 3; e++){
for (f = 0; f < 3; f++){
for (g = 0; g < 3; g++){
printf("%c%c%c%c%c%c%c ",word1[word2[0]][a], word1[word2[1]][b], word1[word2[2]][c], word1[word2[3]][d], word1[word2[4]][e], word1[word2[5]][f], word1[word2[6]][g]);
}
}
}
}
}
}
}
return 0;
}
Main problem is here:
for (i = 6; number == 0; i--)
The loop condition is the opposite of the one it should be. You want to keep iterating on the number until you reach 0 (by successively dividing it by 10).
It should be
for (i = 6; number != 0; i--)
or
for (i = 6; i >= 0; i--)
In addition mind that
if (r == 2){ word2[i] = 0; }
if (r == 3){ word2[i] = 1; }
if (r == 4){ word2[i] = 2; }
if (r == 5){ word2[i] = 3; }
if (r == 6){ word2[i] = 4; }
if (r == 7){ word2[i] = 5; }
if (r == 8){ word2[i] = 6; }
if (r == 9){ word2[i] = 7; }
is equivalent to
if (r >= 2 && r <= 9)
word2[i] = r - 2;
I think this works as you expected:
For some convenience in debugging, I changed some IO format:
Input separated number 2-9 divided by space and end with -1.
The input sequence can be of any length, just end with -1.
For example, input:2 3 4 2 -1
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
char word1[8][3] = {
{ 'A', 'B', 'C' },
{ 'D', 'E', 'F' },
{ 'G', 'H', 'I' },
{ 'J', 'K', 'L' },
{ 'M', 'N', 'O' },
{ 'P', 'R', 'S' },
{ 'T', 'U', 'V' },
{ 'W', 'X', 'Y' } };
void translate(char * headStr,int * pattern,int pos_to_do)
{
if(pattern[pos_to_do]<0)
{
printf("%s\n",headStr);
return;
}
char str[3][20];
int i;
for(i=0;i<3;i++)
{
strcpy(str[i],headStr);
char str_this[2];
str_this[0]=word1[ pattern[pos_to_do] ][i];
str_this[1]='\0';
strcat(str[i],str_this);
translate(str[i],pattern,pos_to_do+1);
}
return;
}
int main(){
int che[20];
int number, check,len;
while (1)
{
printf("Enter digits(except 0 and 1):");
len=0;
scanf(" %d", &number);
while(number>=2)
{
che[len]=number-2;
len++;
scanf("%d", &number);
}
che[len]=-1;
char str_start[]="";
translate(str_start,che,0);
}
return 0;
}
Test output:
Enter digits(except 0 and 1):2 3 4 -1
ADG
ADH
ADI
AEG
AEH
AEI
AFG
AFH
AFI
BDG
BDH
BDI
BEG
BEH
BEI
BFG
BFH
BFI
CDG
CDH
CDI
CEG
CEH
CEI
CFG
CFH
CFI
Enter digits(except 0 and 1):

Resources