2

当我尝试像这样声明一个global二维数组C++

int maxX = 10;
int maxZ = 10;
SDL_Rect mapX[maxX][maxZ];

我收到一条错误消息
error: variable-size type declared outside of any function

4

5 回答 5

8

(乍一看,它在我看来是“C 和 C++ 问题之间的差异”。不过我可能会弄错。)

由于您使用非常量值作为数组大小,因此您正试图声明一个可变长度数组 (VLA)。C++ 根本不支持 VLA,而 C 仅支持本地VLA。后者正是编译器在该错误消息中告诉您的内容。(而且我相信这个错误消息来自 C 编译器,因为 C++ 编译器会给你一个完全不同的错误。)

因此,严格来说,您不能在 C 或 C++ 中声明这样的数组。虽然 C 语言支持 VLA,但它们仍然必须是本地的。不允许在 C 中声明具有静态存储持续时间的 VLA。

在 C++ 中,所有数组都必须具有固定的预先确定的编译时大小。这意味着数组大小必须由编译时常量指定。您使用了非常量值,这就是导致错误的原因。

换句话说,在 C 和 C++ 中,在为具有静态存储持续时间的数组(包括所谓的“全局”数组)指定大小时,都需要使用常量表达式。

在 C++ 中,为了使您的大小保持不变,您必须使用const

const int maxX = 10;
const int maxZ = 10;

在 C 中这是行不通的,因为在 C中,const对象在某种意义上并不是真正的常量,它们不会形成常量表达式。在 C 中你必须使用

#define maxX 10
#define maxZ 10

或者

enum {
  maxX = 10,
  maxZ = 10
};
于 2012-12-25T19:38:57.650 回答
2

在 C++ 中,您不能使用变量来定义数组的大小,因为编译器需要在编译时知道在哪里分配数组的内存以及它需要多少内存。声明maxXmaxZasint使它们成为变量,因此不适合数组维度。但是,如果您将它们声明为const int,那么它们将是常量,并且编译器将知道这些值将在您的程序执行过程中被固定,并且允许使用它们来定义数组维度。

因此,这不起作用:

int maxX = 10;
int maxZ = 10;
SDL_Rect mapX[maxX][maxZ]; // Not allowed

但这很好:

const int maxX = 10;
const int maxZ = 10;
SDL_Rect mapX[maxX][maxZ]; // Allowed
于 2012-12-25T19:28:48.550 回答
1
static const int maxX = 10;
static const int maxZ = 10;
SDL_Rect mapX[maxX][maxZ];

对我来说很好。


笔记

通常,使用全局变量、原始数组或全局原始数组通常不是一个好习惯。显然,我没有足够的上下文来评论这里是否是正确的选择。


历史记录

在现代常量之前,枚举或#define常量以使它们在这种情况下正常工作是很常见的。

于 2012-12-25T19:18:33.607 回答
0

而不是 C 样式的数组,我建议使用std::vector

std::vector< std::vector<SDL_Rect> > mapX;
于 2012-12-25T19:23:53.280 回答
0

我不认为这是使用 SDL_rect 的正确方法。

语法应该像

SDL_Rect rect = {0,0,10,10}

因此,您可以执行以下操作;

int maxX = 10;
int maxZ = 10;
SDL_Rect rect = {0,0,maxX,maxZ}
于 2012-12-25T19:18:21.760 回答