Win a copy of Getting started with Java programming language this week in the Beginning Java forum!
  • Post Reply Bookmark Topic Watch Topic
  • New Topic

anonymous array creation not a statement  RSS feed

 
Richard Hayward
Ranch Hand
Posts: 145
5
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I can usually create object instances without assigning them to any variable.



but not, it seems, if the object I'm creating is an array.

Are arrays the only objects for which this isn't allowed?
 
Paul Anilprem
Enthuware Software Support
Ranch Hand
Posts: 3925
24
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Interesting question. I tried find to something in the JLS about this but didn't find anything specific to this use case.  When you create an unreferenced object of a regular class (such as new String() or whatever), you are doing it for the side effects of the constructor because the object itself will most probably be garbage collected. You should not rely on this though because the JVM may even optimize the call away. So logically, it doesn't make sense to create unreferenced array objects because these array classes do have any user defined code. Other than this, I don't see any reason why this is prohibited.

-Paul.
 
Richard Hayward
Ranch Hand
Posts: 145
5
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Paul Anilprem wrote:When you create an unreferenced object of a regular class (such as new String() or whatever), you are doing it for the side effects of the constructor because the object itself will most probably be garbage collected. You should not rely on this though because the JVM may even optimize the call away.


So I can't be sure that the Dog will bark?

I thought that was guaranteed.
 
Paul Anilprem
Enthuware Software Support
Ranch Hand
Posts: 3925
24
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Richard Hayward wrote:
Paul Anilprem wrote:When you create an unreferenced object of a regular class (such as new String() or whatever), you are doing it for the side effects of the constructor because the object itself will most probably be garbage collected. You should not rely on this though because the JVM may even optimize the call away.


So I can't be sure that the Dog will bark?

I thought that was guaranteed.


I think this is guaranteed. But I am unable to find a definitive source that lists what all is guaranteed. I am sure other experts here will point you to the right source.
 
Stephan van Hulst
Saloon Keeper
Posts: 6846
100
  • Likes 2
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Block: A Block may consist of one or more BlockStatements. A BlockStatement may be either a LocalVariableDeclarationStatement, a ClassDeclaration or a Statement. You already know that you can initialize arrays like this in local variable declarations, and class declarations are not applicable. Let's explore Statement: If we go through the list of things that a Statement can be, the only one that appears like it could be applicable to your situation is the ExpressionStatement. Here's the list of things that an ExpressionStatement can be when terminated by a semi-colon:

  • Assignment
  • PreIncrementExpression
  • PreDecrementExpression
  • PostIncrementExpression
  • PostDecrementExpression
  • MethodInvocation
  • ClassInstanceCreationExpression


  • You're not performing assignment, an increment/decrement operation, a method invocation or class instance creation. Creating an instance of an array is not allowed as a statement by itself. You need to assign it to a variable, and it doesn't matter whether you use an array initializer or not.

    The reason why class instance creation is allowed as a statement by itself, is because constructors can have side effects that a programmer may wish to occur, without doing anything with the new instance. This is not recommended behavior, but APIs are sometimes horribly designed. Array creation never has side-effects though, so creating one without assigning it to a variable is always a mistake.
     
    Stephan van Hulst
    Saloon Keeper
    Posts: 6846
    100
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    I'm pretty sure class instance creations are never optimized away. They might be inlined though, and parts of their inlined code may be optimized away. Side effects will never be removed.
     
    Richard Hayward
    Ranch Hand
    Posts: 145
    5
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Thanks for that link Stephan.

    Stephan van Hulst wrote:You're not performing assignment, an increment/decrement operation, a method invocation or class instance creation.


    That's interesting because I'd assumed that I was performing a 'class instance creation'. However, the jls says

    https://docs.oracle.com/javase/specs/jls/se8/html/jls-4.html#jls-4.3.1

    An object is a class instance or an array.


    so an array, although an object, isn't a class instance. That seems odd to me on two counts.
    Firstly, I can take an array object and ask what its class is, an int[] will report its class as being [I
    Secondly if I get an array's class and then use reflection to examine its constructors, I find that it hasn't got any, so I don't see how the array could have been created.



    However, for the purposes of passing the exam, this seems territory that I won't get tested on, so with thanks to Paul & Stephan, I'm happy to leave it at that.
     
    Stephan van Hulst
    Saloon Keeper
    Posts: 6846
    100
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    https://docs.oracle.com/javase/specs/jls/se8/html/jls-10.html#jls-10.8

    Every array has an associated Class object, shared with all other arrays with the same component type.

    Although an array type is not a class, the Class object of every array acts as if:

  • The direct superclass of every array type is Object.
  • Every array type implements the interfaces Cloneable and java.io.Serializable.
  •  
    Stephan van Hulst
    Saloon Keeper
    Posts: 6846
    100
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Richard Hayward wrote:if I get an array's class and then use reflection to examine its constructors, I find that it hasn't got any, so I don't see how the array could have been created.

    Constructors are members of classes, and arrays aren't class types. Arrays are created using black voodoo magic, the same way instances of Cloneable classes are created when you clone an original.
     
    Richard Hayward
    Ranch Hand
    Posts: 145
    5
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    Thanks for your help, explanations & links Stephan. That covers my concerns & I'll have a look through that bit of the jls.


    Incidentally, looking at the code I posted earlier, to find the constructors in an array class, I should have usedto capture all of them: public, protected, default & private. Makes no difference to my problem (now explained) however, using reflection still reports no constructors.

     
    • Post Reply Bookmark Topic Watch Topic
    • New Topic
    Boost this thread!