Re: new an array of pointers
On Mar 18, 9:11 pm, "Alf P. Steinbach" <al...@start.no> wrote:
* James Kanze:
On 18 Mar, 10:05, thomas <freshtho...@gmail.com> wrote:
----------
int **p = new int *[30]; //OK
Evaluates as:
int** p = new (int (*([30]));
An array of 30 int*.
int **p = new (int) *[30]; //ERROR
int** p = (new (int)) * [30];
Don't know what the compiler is supposed to make of the [30],
given that there's no address expression to the left of it.
(And the '*' is multiplication.)
int **p = new (int*)[30]; //ERROR
int** p = (new (int*))[30];
Here, the initialization expression is a syntactically legal
expression (but would have undefined behavior at runtime),
new expressions are a wilderness of special case rules.
They do have their own particular grammar. The goal, of course,
is to allow the compiler to know where the type ends, and the
initialization expression begins. The result is that while the
compiler now knows, the human reader often has problems.
On reading your statement I thought huh, that must a placement
form syntactically.
No, but I'll bet it would be possible to construct some cases
where that sort of ambiguity would exist.
But as it turned out[1] I was wrong[2] about why you're wrong
here,
<example>
"ComeauTest.c", line 3: error: this operator is not allowed at this point; use
parentheses
int **p = new (int*)[30];
^
"ComeauTest.c", line 3: error: a value of type "int *" cannot be used to initialize
an entity of type "int **"
int **p = new (int*)[30];
</example>
but
it doesn't have the type int**: the new expression returns an
int** (pointing to a single uninitialized int*), but
dereferencing it (remember, a[b] is the same as *(a+b)) results
in an int*.
Right, but first it must pass muster syntactically.
It does. At least according to my copy of the epxression. The
new expression is "new (int*)". And that gets used as the left
operand of the [] expression. I don't know what Comeau is
complaining about with "this operator is not allowed at this
point---the grammar clearly allows it. (The new expression, in
this case, matches "::[opt] new new-placement[opt] ( type-id )
new-initializer[opt]", with none of the optional parts present.
--
James Kanze