警告的原因是什么:"when type is in parentheses, array cannot have dynamic size"?
What is the reason for the warning: "when type is in parentheses, array cannot have dynamic size"?
我已经发布了一个关于与数组的动态内存分配相关的 GCC 错误的问题:
现在使用 Clang HEAD 10.0.0 我收到以下警告:
rog.cc:9:37: warning: when type is in parentheses, array cannot have dynamic size
int ( **a )[N3] = new ( int ( *[n1] )[N3] );
~~ ^~ ~
当我运行这个演示程序时:
#include <cstddef>
int main()
{
const size_t N3 = 4;
size_t n1 = 2;
int ( **a )[N3] = new ( int ( *[n1] )[N3] );
}
使用非常量变量n1
违反了标准的哪一部分?
未加括号的形式使用 new-type-id;括号内的形式使用 type-id。只有 new-type-id 允许动态数组绑定。普通 type-id 没有。 Compare:
new-type-id:
type-specifier-seq new-declarator_opt
new-declarator:
ptr-operator new-declarator_opt
noptr-new-declarator
noptr-new-declarator:
[ expression_opt ] attribute-specifier-seq_opt
noptr-new-declarator [ constant-expression ] attribute-specifier-seq_opt
type-id:
type-specifier-seq abstract-declarator_opt
abstract-declarator:
ptr-abstract-declarator
noptr-abstract-declarator_opt parameters-and-qualifiers trailing-return-type
abstract-pack-declarator
ptr-abstract-declarator:
noptr-abstract-declarator
ptr-operator ptr-abstract-declarator_opt
noptr-abstract-declarator:
noptr-abstract-declarator_opt parameters-and-qualifiers
noptr-abstract-declarator_opt [ constant-expression_opt ] attribute-specifier-seq_opt
( ptr-abstract-declarator )
请注意,noptr-new-declarator 的第一个产生式允许数组绑定为任何 表达式,而 noptr-abstract-declarator 产生式要求绑定是 constant-expression.
new
运算符(是的,它是运算符,不是函数)后面需要一个构造函数调用模板,所以new
关键字后面的第一个标记是类型标识符. C++ 语言允许您通过将类型放在括号中来指定要构建的对象的类型作为某种形式的强制转换,但是该类型不能动态参数化(必须在编译时完全知道)。
去掉外括号就可以了。如
int ( **a )[N3] = new int ( *[n1] )[N3]; // invalid
顺便说一下,在我看来(我没有测试过)代码需要一个 *
来匹配 a
:
的类型
int ( *(*a)[n1] )[N3] = new int ( *[n1] )[N3]; // ERRONEOUS ALSO
(因为 new
总是 returns 指向分配类型的指针)。这将为 a
分配一个指向 n1
指针数组(n1
元素)的指针 N3
指向 int
指针的数组(我认为你需要进一步划分你的类型定义,因为你可能都不理解它)
#include <cstddef>
#define N3 (4)
typedef int(*mytype)[N3];
int main()
{
size_t n1 = 2;
mytype *a = new mytype[n1];
}
问题是 C++ 不允许分配定义为
的类型的数组
type (*);
或其任意组合(在 *
之后需要一个标识符)
我已经发布了一个关于与数组的动态内存分配相关的 GCC 错误的问题:
现在使用 Clang HEAD 10.0.0 我收到以下警告:
rog.cc:9:37: warning: when type is in parentheses, array cannot have dynamic size
int ( **a )[N3] = new ( int ( *[n1] )[N3] );
~~ ^~ ~
当我运行这个演示程序时:
#include <cstddef>
int main()
{
const size_t N3 = 4;
size_t n1 = 2;
int ( **a )[N3] = new ( int ( *[n1] )[N3] );
}
使用非常量变量n1
违反了标准的哪一部分?
未加括号的形式使用 new-type-id;括号内的形式使用 type-id。只有 new-type-id 允许动态数组绑定。普通 type-id 没有。 Compare:
new-type-id:
type-specifier-seq new-declarator_opt
new-declarator:
ptr-operator new-declarator_opt
noptr-new-declarator
noptr-new-declarator:
[ expression_opt ] attribute-specifier-seq_opt
noptr-new-declarator [ constant-expression ] attribute-specifier-seq_opt
type-id:
type-specifier-seq abstract-declarator_opt
abstract-declarator:
ptr-abstract-declarator
noptr-abstract-declarator_opt parameters-and-qualifiers trailing-return-type
abstract-pack-declarator
ptr-abstract-declarator:
noptr-abstract-declarator
ptr-operator ptr-abstract-declarator_opt
noptr-abstract-declarator:
noptr-abstract-declarator_opt parameters-and-qualifiers
noptr-abstract-declarator_opt [ constant-expression_opt ] attribute-specifier-seq_opt
( ptr-abstract-declarator )
请注意,noptr-new-declarator 的第一个产生式允许数组绑定为任何 表达式,而 noptr-abstract-declarator 产生式要求绑定是 constant-expression.
new
运算符(是的,它是运算符,不是函数)后面需要一个构造函数调用模板,所以new
关键字后面的第一个标记是类型标识符. C++ 语言允许您通过将类型放在括号中来指定要构建的对象的类型作为某种形式的强制转换,但是该类型不能动态参数化(必须在编译时完全知道)。
去掉外括号就可以了。如
int ( **a )[N3] = new int ( *[n1] )[N3]; // invalid
顺便说一下,在我看来(我没有测试过)代码需要一个 *
来匹配 a
:
int ( *(*a)[n1] )[N3] = new int ( *[n1] )[N3]; // ERRONEOUS ALSO
(因为 new
总是 returns 指向分配类型的指针)。这将为 a
分配一个指向 n1
指针数组(n1
元素)的指针 N3
指向 int
指针的数组(我认为你需要进一步划分你的类型定义,因为你可能都不理解它)
#include <cstddef>
#define N3 (4)
typedef int(*mytype)[N3];
int main()
{
size_t n1 = 2;
mytype *a = new mytype[n1];
}
问题是 C++ 不允许分配定义为
的类型的数组type (*);
或其任意组合(在 *
之后需要一个标识符)