我正在ANSI C中构建一个生命游戏版本,我几乎已经为它编写了所有代码。
我的C源文件:
#include <stdio.h>
#include <stdlib.h>
#define HEIGHT 32
#define WIDTH 32
#define COMPASS 8
#define SPACE '.'
unsigned long mask = 0x80000000;
unsigned long neighbours[COMPASS] = { 0 };
unsigned long row[WIDTH] = { 0 };
unsigned long copy[WIDTH] = { 0 };
int northWest(unsigned long row, int rowNum) {
copy[rowNum - 1] = row >>= 1;
return copy[rowNum - 1];
}
int north(unsigned long row, int rowNum) {
copy[rowNum - 1] = row;
return copy[rowNum - 1];
}
int northEast(unsigned long row, int rowNum) {
copy[rowNum - 1] = row <<= 1;
return copy[rowNum - 1];
}
int west(unsigned long row, int rowNum) {
copy[rowNum] = row >>= 1;
return copy[rowNum];
}
int east(unsigned long row, int rowNum) {
copy[rowNum] = row <<= 1;
return copy[rowNum];
}
int southWest(unsigned long row, int rowNum) {
copy[rowNum + 1] = row >>= 1;
return copy[rowNum + 1];
}
int south(unsigned long row, int rowNum) {
copy[rowNum + 1] = row;
return copy[rowNum + 1];
}
int southEast(unsigned long row, int rowNum) {
copy[rowNum + 1] = row <<= 1;
return copy[rowNum + 1];
}
/*void clearRows(unsigned long row[]) {
int i;
system("clear");
for (i = 0; i < HEIGHT; ++i) {
row[i] = 0;
}
}*/
void displayBinary(unsigned long x) {
int bit;
int mask;
for (bit = 0; bit < HEIGHT; ++bit) {
mask = 1 << bit;
printf("%c", (x & mask) ? 'X' : SPACE);
}
printf("\n");
}
int main(void) {
int i, alive;
char ch;
unsigned long init32;
srand(time(NULL));
for (i = 0; i < HEIGHT; ++i) {
init32 = ((double)rand() / RAND_MAX) * 0xFFFFFFFF;
row[i] = init32;
displayBinary(row[i]);
}
do {
system("clear");
for (i = 0; i < HEIGHT; ++i) {
neighbours[0] = north(row[i], i);
neighbours[1] = south(row[i], i);
neighbours[2] = west(row[i], i);
neighbours[3] = east(row[i], i);
neighbours[4] = northWest(row[i], i);
neighbours[5] = northEast(row[i], i);
neighbours[6] = southEast(row[i], i);
neighbours[7] = southWest(row[i], i);
}
for (i = 0; i < HEIGHT; ++i) {
alive += ((mask & neighbours[i]) ? 1 : 0);
displayBinary(row[i]);
}
} while ((ch = getchar()) != 'n');
return EXIT_SUCCESS;
}
我的目标是在32x32板上打印随机的'X'字符,并且只要用户不输入'n'就有程序循环。对于每个循环迭代,我希望每个坐标检查其邻居并且如果它具有少于两个邻居或多于三个邻居则“死”。否则,它“生命”并在该坐标处打印“X”。
我理解使用按位ANDing可能不是完成此操作的最佳方法,但我的教授已经要求我们使用按位AND,因此我无法改变这种逻辑。
我无法清除循环之间的行。有人可以帮我弄清楚如何为do循环的每次迭代打印更新的行吗?
非常感谢任何帮助。谢谢。
答案 0 :(得分:2)
为了显示正在发生的事情,我添加了这个定义,
//#define SPACE (0x20)
#define SPACE ('.')
然后我改变了打印空间的两个实例,
printf("%c", 0x20);
到
printf("%c", SPACE);
然后运行你的程序并得到一行,有一些“。”和一些“X”,但第二次传递导致所有“。”,
看起来您对相邻节点的计算可能是错误的。
为什么您的打印出现错误?
因为你的第一个COMPASS循环使用了displayBinary()8次,
for (i = 0; i < COMPASS; ++i) {
init32 = ((double)rand() / RAND_MAX) * 0xFFFFFFFF;
row[i] = init32;
displayBinary(row[i]);
}
虽然你的后续外观使用printf(而不是调用displayBinary),但是8次只能打印8个字符,
for (i = 0; i < COMPASS; ++i) {
alive += ((mask & row[i]) ? 1 : 0);
if ((alive == 2) || (alive == 3))
printf("%c", 'X');
else
printf("%c", SPACE);
}
您的HEIGHT循环会重新计算邻居[],但您应该重置行[]。
我重写了你的displayBinary函数,这显示了整行,
void displayBinary(unsigned long x) {
//do {
// printf("%c", (x & mask) ? 'X' : SPACE);
//} while ((mask >>= 1) != 0);
int bit;
int mask;
for( bit=0; bit<32; ++bit )
{
mask = 1<<bit;
printf("%c", (x & mask) ? 'X' : SPACE);
}
printf("\n");
}