/// <summary>
        /// Deep-clone the code object.
        /// </summary>
        public override CodeObject Clone()
        {
            NewOperator clone = (NewOperator)base.Clone();

            clone.CloneField(ref clone._initializer, _initializer);
            return(clone);
        }
        /// <summary>
        /// Parse a <see cref="NewObject"/> or <see cref="NewArray"/> operator.
        /// </summary>
        public static NewOperator Parse(Parser parser, CodeObject parent, ParseFlags flags)
        {
            // Abort if our parent is a TypeDecl (the 'new' is probably part of a method declaration)
            if (parent is TypeDecl)
            {
                return(null);
            }

            NewOperator result = null;

            // Peek ahead to see if we have a valid non-array type
            TypeRefBase.PeekType(parser, parser.PeekNextToken(), true, flags | ParseFlags.Type);
            Token token = parser.LastPeekedToken;

            if (token != null)
            {
                // If we found a '[', assume NewArray
                if (token.Text == NewArray.ParseTokenStart)
                {
                    result = new NewArray(parser, parent);
                }
                // If we found '(' or '{', assume NewObject
                else if (token.Text == ParameterDecl.ParseTokenStart || token.Text == Initializer.ParseTokenStart)
                {
                    result = new NewObject(parser, parent);
                }
            }

            // Last chance - invalid code might still parse better as a NewObject, so assume that's
            // what it is if our parent is a VariableDecl.
            if (result == null && parent is VariableDecl)
            {
                result = new NewObject(parser, parent);
            }

            // If we didn't create an object, return null (the 'new' is probably part of a method declaration)
            return(result);
        }