Primary Expressions

15.8 Primary Expressions

Primary expressions include most of the simplest kinds of expressions, from which all others are constructed: literals, class literals, field accesses, method invocations, and array accesses. A parenthesized expression is also treated syntactically as a primary expression.

Primary: PrimaryNoNewArray ArrayCreationExpression

PrimaryNoNewArray: Literal Type . class

void . class this ClassName . this ( Expression ) ClassInstanceCreationExpression FieldAccess MethodInvocation ArrayAccess

EXPRESSIONS Lexical Literals 15.8.1

This part of the grammar of the Java programming language is unusual, in two ways. First, one might expect simple names, such as names of local variables and method parameters, to be primary expressions. For technical reasons, names are grouped together with primary expressions a little later when postfix expressions are introduced (§15.14).

The technical reasons have to do with allowing left-to-right parsing of Java programs with only one-token lookahead. Consider the expressions (z[3]) and (z[]) . The first is a parenthesized array access (§15.13) and the second is the start of a cast (§15.16). At the point that the look-ahead symbol is [ , a left-to-right parse will have reduced the z to the nonterminal Name. In the context of a cast we prefer not to have to reduce the name to

a Primary, but if Name were one of the alternatives for Primary, then we could not tell whether to do the reduction (that is, we could not determine whether the current situation would turn out to be a parenthesized array access or a cast) without looking ahead two tokens, to the token following the [ . The Java grammar presented here avoids the problem by keeping Name and Primary separate and allowing either in certain other syntax rules (those for MethodInvocation, ArrayAccess, PostfixExpression, but not for FieldAccess, because this uses an identifier directly). This strategy effectively defers the question of whether a Name should be treated as a Primary until more context can be examined.

The second unusual feature avoids a potential grammatical ambiguity in the expression " new int[3][3] " which in Java always means a single creation of a multidimensional array, but which, without appropriate grammatical finesse, might also be interpreted as meaning the same as " (new int[3])[3] ".

This ambiguity is eliminated by splitting the expected definition of Primary into Primary and PrimaryNoNewArray. (This may be compared to the splitting of Statement into Statement and StatementNoShortIf (§14.5) to avoid the "dangling else" problem.)

15.8.1 Lexical Literals

A literal (§3.10) denotes a fixed, unchanging value. The following production from §3.10 is repeated here for convenience:

Literal: IntegerLiteral FloatingPointLiteral BooleanLiteral CharacterLiteral StringLiteral NullLiteral

The type of a literal is determined as follows: • The type of an integer literal (§3.10.1) that ends with L or l is long (§4.2.1).

The type of any other integer literal is int (§4.2.1).

15.8.2 Class Literals EXPRESSIONS

• The type of a floating-point literal (§3.10.2) that ends with F or f is float and its value must be an element of the float value set (§4.2.3).

The type of any other floating-point literal is double and its value must be an element of the double value set (§4.2.3).

• The type of a boolean literal (§3.10.3) is boolean (§4.2.5). • The type of a character literal (§3.10.4) is char (§4.2.1). • The type of a string literal (§3.10.5) is String (§4.3.3). • The type of the null literal null (§3.10.7) is the null type (§4.1); its value is the

null reference. Evaluation of a lexical literal always completes normally.

15.8.2 Class Literals

A class literal is an expression consisting of the name of a class, interface, array, or primitive type, or the pseudo-type void , followed by a ' . ' and the token class .

The type of C .class , where C is the name of a class, interface, or array type (§4.3), is Class<C> .

The type of p .class , where p is the name of a primitive type (§4.2), is Class<B> , where B is the type of an expression of type p after boxing conversion (§5.1.7).

The type of void.class (§8.4.5) is Class<Void> . It is a compile-time error if the named type is a type variable (§4.4) or a

parameterized type (§4.5) or an array whose element type is a type variable or parameterized type.

It is a compile-time error if the named type does not denote a type that is accessible (§6.6) and in scope (§6.3) at the point where the class literal appears.

A class literal evaluates to the Class object for the named type (or for void ) as defined by the defining class loader (§12.2) of the class of the current instance.

15.8.3 this The keyword this may be used only in the body of an instance method, instance

initializer, or constructor, or in the initializer of an instance variable of a class. If it appears anywhere else, a compile-time error occurs.

EXPRESSIONS Qualified this 15.8.4

When used as a primary expression, the keyword this denotes a value that is a reference to the object for which the instance method was invoked (§15.12), or to the object being constructed.

The type of this is the class C within which the keyword this occurs. At run-time, the class of the actual object referred to may be the class C or any

subclass of C . The keyword this is also used in a special explicit constructor invocation

statement, which can appear at the beginning of a constructor body (§8.8.7).

Example 15.8.3-1. The this Expression

class IntVector { int[] v; boolean equals(IntVector other) {

if (this == other) return true; if (v.length != other.v.length) return false; for (int i = 0; i < v.length; i++) { if (v[i] != other.v[i]) return false; } return true;

Here, the class IntVector implements a method equals , which compares two vectors. If the other vector is the same vector object as the one for which the equals method was invoked, then the check can skip the length and value comparisons. The equals method implements this check by comparing the reference to the other object to this .

15.8.4 Qualified this Any lexically enclosing instance (§8.1.3) can be referred to by explicitly qualifying

the keyword this . Let C be the class denoted by ClassName. Let n be an integer such that C is the

n'th lexically enclosing class of the class in which the qualified this expression appears.

The value of an expression of the form ClassName .this is the n'th lexically enclosing instance of this .

The type of the expression is C .

It is a compile-time error if the current class is not an inner class of class C or C itself.

15.8.5 Parenthesized Expressions EXPRESSIONS

15.8.5 Parenthesized Expressions

A parenthesized expression is a primary expression whose type is the type of the contained expression and whose value at run-time is the value of the contained expression. If the contained expression denotes a variable then the parenthesized expression also denotes that variable.

The use of parentheses affects only the order of evaluation, except for a corner case whereby (-2147483648) and (-9223372036854775808L) are legal but - (2147483648) and -(9223372036854775808L) are illegal.

This is because the decimal literals 2147483648 and 9223372036854775808L are allowed only as an operand of the unary minus operator (§3.10.1).

In particular, the presence or absence of parentheses around an expression does not (except for the case noted above) affect in any way:

• the choice of value set (§4.2.3) for the value of an expression of type float or

double

• whether a variable is definitely assigned, definitely assigned when true , definitely assigned when false , definitely unassigned, definitely unassigned when true , or definitely unassigned when false (§16)