在 c 中初始化 2d 字符数组 - tic tac toe 游戏
Initialize 2d char array in c - tic tac toe game
我在尝试用 c 编写井字游戏时感到困惑。我正在关注一本书,该书使用一个包含 8 个元素的字符数组来创建电路板。我知道一个数组 [8] 包含 9 个元素,但是如果数组被声明为 char 数组,因为它必须包含空格来为游戏制作空板,它不应该是数组 [9],因为它必须包含 9 个字符和一个空字符 '\0'?在将电路板转换为二维数组时我也有同样的疑问,因为我知道电路板应该用数组 [3][3] 制作,但是如果我想将它声明为 char,那么空字符?
二维数组本质上是一维数组,为程序员增加了易用性。您阅读的书可能只是将值存储在单元格中,并将它们显示出来,而不是像您所说的那样将一大块字符显示为字符串。这比将整个板存储为字符串更有效。
假设您要存储一个 4x4 面积的二维数组。您可以将其表示为大小为 16 的一维数组,并像这样访问索引:
arr[j + i * 4]
j 是你在那个 4 单元块中的位置,i 是你所在的 4 单元块。
此外,大小为 [8] 的数组有 8 个元素。例如:
char arr[8]; // has 8 elements, not 9
I know an array[8] contains 9 elements
不,为什么会这样?定义为 int arry[8]
的数组仅包含 8 个元素。同样,在 C 中,数组索引是基于 0 的,这意味着对于上述数组,只有 array[0]
到 array[7]
是有效访问。
也就是说,对于 char
数组,要用作 字符串 ,也应该有 space 作为空终止符。所以,如果你想要一个包含 9 个元素的 char
数组并想将它用作 字符串 ,你需要将它定义为 char[10]
.
使用字符作为数组的值与 char
的数组可以衰减为指针 char*
并被解释为 NUL
的事实无关终止字符串。
字符串在 C 语言中没有特定的类型,它只是一种解释某些数据的方式。所以你混合了两个概念。
一个 char
数组不必 NUL
终止,如果你打算将它与将数据用作字符串的函数一起使用,它需要 NUL
终止.
char board[3][3]
是完全合法的,并且有 9 个字符元素的空间,它不需要 [=17=]
,因为您不会将该数据用作字符串。
如果使用字符数组存储字符串,则需要终止零。
对于您的任务,无需在数组中存储字符串。
因此在 C 中,您可以通过以下方式声明例如 3*3 数组
char board[3][3] =
{
" ", // three spaces
" ",
" "
};
数组的每个元素都不会包含终止零,尽管它是由字符串文字初始化的。
另一方面,如果您认为输出这样的数组会更简单,则可以在每个元素中包含终止零。在这种情况下,数组应该定义为
char board[3][4] =
// ^^^
{
" ", // three spaces
" ",
" "
};
至于你的说法
an array[8] contains 9 elements
然后数组被声明为恰好有八个元素。 :)
我认为你的意思是字符串文字。例如,由于存储在文字中的终止零,C 中的字符串文字 "Hi"
具有类型 char[3]
。
一个字符数组可以在任何位置保存任何值。只有当您想要使用某些函数时,您才需要确保字符串末尾有一个 NUL 字符(即 0
,而不是 '0'
!)——它告诉函数什么时候停止处理!
所以:char john[4] = { 'J', 'o', 'h', 'n' };
是完全合法的 - 只是不要将 john
传递给 strlen()
,因为它会一直计数直到找到 0
值,并且数组中没有!
此外:char tictactoe[3][3];
在任何地方都不需要 0
- 除非你尝试将 整个 数组传递给 printf()
原因...
请注意,您可以安全地执行以下操作:
printf(" %c | %c | %c \n", tictactoe[0][0], tictactoe[0][1], tictactoe[0][2]);
printf("---+---+---\n");
printf(" %c | %c | %c \n", tictactoe[1][0], tictactoe[1][1], tictactoe[1][2]);
printf("---+---+---\n");
printf(" %c | %c | %c \n", tictactoe[2][0], tictactoe[2][1], tictactoe[2][2]);
因为使用 %c
意味着 "print one character",而不是 "print a string of characters"。
以 NUL 结尾的字符串形式通常称为 ASCIIZ(ASCII-Zeroed)字符串,这也是九个字符的数组只能容纳八个字符的字符串的原因(与什么相反)你说的)-它需要第九个来保持 NUL。
而且,和 C 中一样,任何数组都从 0 到长度为 1,因此在我的示例中 [0]
、[1]
和 [2]
我在尝试用 c 编写井字游戏时感到困惑。我正在关注一本书,该书使用一个包含 8 个元素的字符数组来创建电路板。我知道一个数组 [8] 包含 9 个元素,但是如果数组被声明为 char 数组,因为它必须包含空格来为游戏制作空板,它不应该是数组 [9],因为它必须包含 9 个字符和一个空字符 '\0'?在将电路板转换为二维数组时我也有同样的疑问,因为我知道电路板应该用数组 [3][3] 制作,但是如果我想将它声明为 char,那么空字符?
二维数组本质上是一维数组,为程序员增加了易用性。您阅读的书可能只是将值存储在单元格中,并将它们显示出来,而不是像您所说的那样将一大块字符显示为字符串。这比将整个板存储为字符串更有效。
假设您要存储一个 4x4 面积的二维数组。您可以将其表示为大小为 16 的一维数组,并像这样访问索引:
arr[j + i * 4]
j 是你在那个 4 单元块中的位置,i 是你所在的 4 单元块。
此外,大小为 [8] 的数组有 8 个元素。例如:
char arr[8]; // has 8 elements, not 9
I know an array[8] contains 9 elements
不,为什么会这样?定义为 int arry[8]
的数组仅包含 8 个元素。同样,在 C 中,数组索引是基于 0 的,这意味着对于上述数组,只有 array[0]
到 array[7]
是有效访问。
也就是说,对于 char
数组,要用作 字符串 ,也应该有 space 作为空终止符。所以,如果你想要一个包含 9 个元素的 char
数组并想将它用作 字符串 ,你需要将它定义为 char[10]
.
使用字符作为数组的值与 char
的数组可以衰减为指针 char*
并被解释为 NUL
的事实无关终止字符串。
字符串在 C 语言中没有特定的类型,它只是一种解释某些数据的方式。所以你混合了两个概念。
一个 char
数组不必 NUL
终止,如果你打算将它与将数据用作字符串的函数一起使用,它需要 NUL
终止.
char board[3][3]
是完全合法的,并且有 9 个字符元素的空间,它不需要 [=17=]
,因为您不会将该数据用作字符串。
如果使用字符数组存储字符串,则需要终止零。
对于您的任务,无需在数组中存储字符串。
因此在 C 中,您可以通过以下方式声明例如 3*3 数组
char board[3][3] =
{
" ", // three spaces
" ",
" "
};
数组的每个元素都不会包含终止零,尽管它是由字符串文字初始化的。
另一方面,如果您认为输出这样的数组会更简单,则可以在每个元素中包含终止零。在这种情况下,数组应该定义为
char board[3][4] =
// ^^^
{
" ", // three spaces
" ",
" "
};
至于你的说法
an array[8] contains 9 elements
然后数组被声明为恰好有八个元素。 :)
我认为你的意思是字符串文字。例如,由于存储在文字中的终止零,C 中的字符串文字 "Hi"
具有类型 char[3]
。
一个字符数组可以在任何位置保存任何值。只有当您想要使用某些函数时,您才需要确保字符串末尾有一个 NUL 字符(即 0
,而不是 '0'
!)——它告诉函数什么时候停止处理!
所以:char john[4] = { 'J', 'o', 'h', 'n' };
是完全合法的 - 只是不要将 john
传递给 strlen()
,因为它会一直计数直到找到 0
值,并且数组中没有!
此外:char tictactoe[3][3];
在任何地方都不需要 0
- 除非你尝试将 整个 数组传递给 printf()
原因...
请注意,您可以安全地执行以下操作:
printf(" %c | %c | %c \n", tictactoe[0][0], tictactoe[0][1], tictactoe[0][2]);
printf("---+---+---\n");
printf(" %c | %c | %c \n", tictactoe[1][0], tictactoe[1][1], tictactoe[1][2]);
printf("---+---+---\n");
printf(" %c | %c | %c \n", tictactoe[2][0], tictactoe[2][1], tictactoe[2][2]);
因为使用 %c
意味着 "print one character",而不是 "print a string of characters"。
以 NUL 结尾的字符串形式通常称为 ASCIIZ(ASCII-Zeroed)字符串,这也是九个字符的数组只能容纳八个字符的字符串的原因(与什么相反)你说的)-它需要第九个来保持 NUL。
而且,和 C 中一样,任何数组都从 0 到长度为 1,因此在我的示例中 [0]
、[1]
和 [2]