/// <summary>
        ///     Resolve property <paramref name="name" /> off the <paramref name="valueExpr" />.
        /// </summary>
        internal ValueExpression ResolvePropertyAccess(DbExpression valueExpr, string name, ErrorContext errCtx)
        {
            DbExpression propertyExpr;

            if (TryResolveAsPropertyAccess(valueExpr, name, out propertyExpr))
            {
                return(new ValueExpression(propertyExpr));
            }

            if (TryResolveAsRefPropertyAccess(valueExpr, name, errCtx, out propertyExpr))
            {
                return(new ValueExpression(propertyExpr));
            }

            if (TypeSemantics.IsCollectionType(valueExpr.ResultType))
            {
                var message = Strings.NotAMemberOfCollection(name, valueExpr.ResultType.EdmType.FullName);
                throw EntitySqlException.Create(errCtx, message, null);
            }
            else
            {
                var message = Strings.NotAMemberOfType(name, valueExpr.ResultType.EdmType.FullName);
                throw EntitySqlException.Create(errCtx, message, null);
            }
        }
示例#2
0
        public void GroupSum1()
        {
            var       esql = "select o.OrderId, sum(o.UnitPrice) from OrderDetails as o";
            Exception ee   = null;

            try
            {
                ef.CreateQuery <IDataRecord>(esql).Execute(MergeOption.NoTracking);
            }
            catch (Exception exc)
            {
                ee = exc;
                Console.WriteLine(exc.Message);
            }
            Assert.IsNotNull(ee);

            EntitySqlException e = null;

            try
            {
                db.CreateQuery(esql).Execute();
            }
            catch (EntitySqlException exc)
            {
                e = exc;
                Console.WriteLine(exc.Message);
            }

            Assert.IsNotNull(e);
            AssertAreEqual(() => Res.InvalidGroupIdentifierReference, e.ErrorName);
        }
示例#3
0
        // <summary>
        // Declares inline function in the query local metadata.
        // </summary>
        internal void DeclareInlineFunction(string name, InlineFunctionInfo functionInfo)
        {
            DebugCheck.NotEmpty(name);
            DebugCheck.NotNull(functionInfo);

            List <InlineFunctionInfo> overloads;

            if (!_functionDefinitions.TryGetValue(name, out overloads))
            {
                overloads = new List <InlineFunctionInfo>();
                _functionDefinitions.Add(name, overloads);
            }

            //
            // Check overload uniqueness.
            //
            if (overloads.Exists(
                    overload =>
                    overload.Parameters.Select(p => p.ResultType).SequenceEqual(
                        functionInfo.Parameters.Select(p => p.ResultType), TypeUsageStructuralComparer.Instance)))
            {
                var errCtx  = functionInfo.FunctionDefAst.ErrCtx;
                var message = Strings.DuplicatedInlineFunctionOverload(name);
                throw EntitySqlException.Create(errCtx, message, null);
            }

            overloads.Add(functionInfo);
        }
示例#4
0
        // <summary>
        // Initializes identifier.
        // </summary>
        internal Identifier(string name, bool isEscaped, string query, int inputPos)
            : base(query, inputPos)
        {
            // name may be empty in the case of "byte[]".
            // "byte" and "[]" come in as two identifiers where second one is escaped and empty.

            Debug.Assert(isEscaped || name[0] != '[', "isEscaped || name[0] != '['");

            if (!isEscaped)
            {
                var isIdentifierASCII = true;
                if (!CqlLexer.IsLetterOrDigitOrUnderscore(name, out isIdentifierASCII))
                {
                    if (isIdentifierASCII)
                    {
                        var errCtx  = ErrCtx;
                        var message = Strings.InvalidSimpleIdentifier(name);
                        throw EntitySqlException.Create(errCtx, message, null);
                    }
                    else
                    {
                        var errCtx  = ErrCtx;
                        var message = Strings.InvalidSimpleIdentifierNonASCII(name);
                        throw EntitySqlException.Create(errCtx, message, null);
                    }
                }
            }

            _name      = name;
            _isEscaped = isEscaped;
        }
        private static object DefaultNumericConversion(string numericString, ErrorContext errCtx)
        {
            if (-1 != numericString.IndexOfAny(Literal._floatTokens))
            {
                double result;
                if (!double.TryParse(numericString, NumberStyles.Float, (IFormatProvider)CultureInfo.InvariantCulture, out result))
                {
                    string errorMessage = Strings.CannotConvertNumericLiteral((object)numericString, (object)"double");
                    throw EntitySqlException.Create(errCtx, errorMessage, (Exception)null);
                }
                return((object)result);
            }
            int result1;

            if (int.TryParse(numericString, NumberStyles.Integer, (IFormatProvider)CultureInfo.InvariantCulture, out result1))
            {
                return((object)result1);
            }
            long result2;

            if (!long.TryParse(numericString, NumberStyles.Integer, (IFormatProvider)CultureInfo.InvariantCulture, out result2))
            {
                string errorMessage = Strings.CannotConvertNumericLiteral((object)numericString, (object)"long");
                throw EntitySqlException.Create(errCtx, errorMessage, (Exception)null);
            }
            return((object)result2);
        }
        internal ExpressionResolution ResolveSimpleName(string name, bool leftHandSideOfMemberAccess, ErrorContext errCtx)
        {
            DebugCheck.NotEmpty(name);

            //
            // Try resolving as a scope entry.
            //
            ScopeEntry scopeEntry;
            int        scopeIndex;

            if (TryScopeLookup(name, out scopeEntry, out scopeIndex))
            {
                //
                // Check for invalid join left expression correlation.
                //
                if (scopeEntry.EntryKind == ScopeEntryKind.SourceVar &&
                    ((SourceScopeEntry)scopeEntry).IsJoinClauseLeftExpr)
                {
                    var message = Strings.InvalidJoinLeftCorrelation;
                    throw EntitySqlException.Create(errCtx, message, null);
                }

                //
                // Set correlation flag.
                //
                SetScopeRegionCorrelationFlag(scopeIndex);

                return(new ValueExpression(GetExpressionFromScopeEntry(scopeEntry, scopeIndex, name, errCtx)));
            }

            //
            // Try resolving as a member of the default entity container.
            //
            var defaultEntityContainer = TypeResolver.Perspective.GetDefaultContainer();
            ExpressionResolution defaultEntityContainerResolution;

            if (defaultEntityContainer != null &&
                TryResolveEntityContainerMemberAccess(defaultEntityContainer, name, out defaultEntityContainerResolution))
            {
                return(defaultEntityContainerResolution);
            }

            if (!_ignoreEntityContainerNameResolution)
            {
                //
                // Try resolving as an entity container.
                //
                EntityContainer entityContainer;
                if (TypeResolver.Perspective.TryGetEntityContainer(
                        name, _parserOptions.NameComparisonCaseInsensitive /*ignoreCase*/, out entityContainer))
                {
                    return(new EntityContainerExpression(entityContainer));
                }
            }

            //
            // Otherwise, resolve as an unqualified name.
            //
            return(TypeResolver.ResolveUnqualifiedName(name, leftHandSideOfMemberAccess /* partOfQualifiedName */, errCtx));
        }
示例#7
0
 private bool IsEscapedIdentifier(string symbol, out Token identifierToken)
 {
     if (symbol.Length > 1 &&
         symbol[0] == '[')
     {
         if (symbol[symbol.Length - 1] == ']')
         {
             var name = symbol.Substring(1, symbol.Length - 2);
             var id   = new Identifier(name, true, _query, _iPos);
             id.ErrCtx.ErrorContextInfo = EntityRes.CtxEscapedIdentifier;
             identifierToken            = NewToken(CqlParser.ESCAPED_IDENTIFIER, id);
             return(true);
         }
         else
         {
             var errorMessage = Strings.InvalidEscapedIdentifier(symbol);
             throw EntitySqlException.Create(_query, errorMessage, _iPos, null, false, null);
         }
     }
     else
     {
         identifierToken = null;
         return(false);
     }
 }
示例#8
0
 internal static void ReportAliasAlreadyUsedError(
     string aliasName,
     ErrorContext errCtx,
     string contextMessage)
 {
     throw EntitySqlException.Create(errCtx, string.Format((IFormatProvider)CultureInfo.InvariantCulture, "{0} {1}", (object)Strings.AliasNameAlreadyUsed((object)aliasName), (object)contextMessage), (Exception)null);
 }
示例#9
0
        internal ExpressionResolution ResolveSimpleName(
            string name,
            bool leftHandSideOfMemberAccess,
            ErrorContext errCtx)
        {
            ScopeEntry scopeEntry;
            int        scopeIndex;

            if (this.TryScopeLookup(name, out scopeEntry, out scopeIndex))
            {
                if (scopeEntry.EntryKind == ScopeEntryKind.SourceVar && ((SourceScopeEntry)scopeEntry).IsJoinClauseLeftExpr)
                {
                    string joinLeftCorrelation = Strings.InvalidJoinLeftCorrelation;
                    throw EntitySqlException.Create(errCtx, joinLeftCorrelation, (Exception)null);
                }
                this.SetScopeRegionCorrelationFlag(scopeIndex);
                return((ExpressionResolution) new ValueExpression(this.GetExpressionFromScopeEntry(scopeEntry, scopeIndex, name, errCtx)));
            }
            EntityContainer      defaultContainer = this.TypeResolver.Perspective.GetDefaultContainer();
            ExpressionResolution resolution;

            if (defaultContainer != null && this.TryResolveEntityContainerMemberAccess(defaultContainer, name, out resolution))
            {
                return(resolution);
            }
            EntityContainer entityContainer;

            if (!this._ignoreEntityContainerNameResolution && this.TypeResolver.Perspective.TryGetEntityContainer(name, this._parserOptions.NameComparisonCaseInsensitive, out entityContainer))
            {
                return((ExpressionResolution) new EntityContainerExpression(entityContainer));
            }
            return((ExpressionResolution)this.TypeResolver.ResolveUnqualifiedName(name, leftHandSideOfMemberAccess, errCtx));
        }
示例#10
0
        /// <summary>
        ///     Performs conversion of numeric strings that have no type suffix hint.
        /// </summary>
        private static object DefaultNumericConversion(string numericString, ErrorContext errCtx)
        {
            if (-1
                != numericString.IndexOfAny(_floatTokens))
            {
                Double value;
                if (!Double.TryParse(numericString, NumberStyles.Float, CultureInfo.InvariantCulture, out value))
                {
                    var message = Strings.CannotConvertNumericLiteral(numericString, "double");
                    throw EntitySqlException.Create(errCtx, message, null);
                }

                return(value);
            }
            else
            {
                Int32 int32Value;
                if (Int32.TryParse(numericString, NumberStyles.Integer, CultureInfo.InvariantCulture, out int32Value))
                {
                    return(int32Value);
                }

                Int64 int64Value;
                if (!Int64.TryParse(numericString, NumberStyles.Integer, CultureInfo.InvariantCulture, out int64Value))
                {
                    var message = Strings.CannotConvertNumericLiteral(numericString, "long");
                    throw EntitySqlException.Create(errCtx, message, null);
                }

                return(int64Value);
            }
        }
示例#11
0
        internal void AssertException(Expression <Func <string> > msgExpr, EntitySqlException exc)
        {
            var memberExpr = (MemberExpression)msgExpr.Body;
            var member     = (PropertyInfo)memberExpr.Member;
            var errorName  = member.Name;

            Assert.AreEqual(errorName, exc.ErrorName);
        }
示例#12
0
 internal static void ReportIncompatibleCommonType(
     ErrorContext errCtx,
     TypeUsage leftType,
     TypeUsage rightType)
 {
     CqlErrorHelper.ReportIncompatibleCommonType(errCtx, leftType, rightType, leftType, rightType);
     throw EntitySqlException.Create(errCtx, Strings.ArgumentTypesAreIncompatible((object)leftType.Identity, (object)rightType.Identity), (Exception)null);
 }
示例#13
0
        internal MetadataMember ResolveMetadataMemberAccess(MetadataMember qualifier, string name, ErrorContext errCtx)
        {
            var fullName = GetFullName(qualifier.Name, name);

            if (qualifier.MetadataMemberClass
                == MetadataMemberClass.Namespace)
            {
                //
                // Try resolving as a type.
                //
                MetadataType type;
                if (TryGetTypeFromMetadata(fullName, out type))
                {
                    return(type);
                }

                //
                // Try resolving as a function.
                //
                MetadataFunctionGroup function;
                if (TryGetFunctionFromMetadata(qualifier.Name, name, out function))
                {
                    return(function);
                }

                //
                // Otherwise, resolve as a namespace.
                //
                return(new MetadataNamespace(fullName));
            }
            else if (qualifier.MetadataMemberClass
                     == MetadataMemberClass.Type)
            {
                var type = (MetadataType)qualifier;
                if (TypeSemantics.IsEnumerationType(type.TypeUsage))
                {
                    EnumMember member;
                    if (_perspective.TryGetEnumMember(
                            (EnumType)type.TypeUsage.EdmType, name, _parserOptions.NameComparisonCaseInsensitive /*ignoreCase*/, out member))
                    {
                        Debug.Assert(member != null, "member != null");
                        Debug.Assert(
                            _parserOptions.NameComparer.Equals(name, member.Name), "_parserOptions.NameComparer.Equals(name, member.Name)");
                        return(new MetadataEnumMember(fullName, type.TypeUsage, member));
                    }
                    else
                    {
                        var message = Strings.NotAMemberOfType(name, qualifier.Name);
                        throw EntitySqlException.Create(errCtx, message, null);
                    }
                }
            }

            var message1 = Strings.InvalidMetadataMemberClassResolution(
                qualifier.Name, qualifier.MetadataMemberClassName, MetadataNamespace.NamespaceClassName);

            throw EntitySqlException.Create(errCtx, message1, null);
        }
示例#14
0
 internal AliasedExpr(Node expr, Identifier alias)
 {
     if (string.IsNullOrEmpty(alias.Name))
     {
         throw EntitySqlException.Create(alias.ErrCtx, Strings.InvalidEmptyIdentifier, (Exception)null);
     }
     this._expr  = expr;
     this._alias = alias;
 }
示例#15
0
 internal void AddNamespaceImport(MetadataNamespace @namespace, ErrorContext errCtx)
 {
     if (this._namespaces.Contains(@namespace))
     {
         string errorMessage = Strings.NamespaceAlreadyImported((object)@namespace.Name);
         throw EntitySqlException.Create(errCtx, errorMessage, (Exception)null);
     }
     this._namespaces.Add(@namespace);
 }
示例#16
0
 internal QueryParameter(string parameterName, string query, int inputPos)
     : base(query, inputPos)
 {
     this._name = parameterName.Substring(1);
     if (this._name.StartsWith("_", StringComparison.OrdinalIgnoreCase) || char.IsDigit(this._name, 0))
     {
         throw EntitySqlException.Create(this.ErrCtx, Strings.InvalidParameterFormat((object)this._name), (Exception)null);
     }
 }
示例#17
0
        private static Exception AmbiguousMetadataMemberName(
            ErrorContext errCtx,
            string name,
            MetadataNamespace ns1,
            MetadataNamespace ns2)
        {
            string errorMessage = Strings.AmbiguousMetadataMemberName((object)name, (object)ns1.Name, (object)ns2?.Name);

            throw EntitySqlException.Create(errCtx, errorMessage, (Exception)null);
        }
示例#18
0
        // <summary>
        // Adds a non-aliased namespace import.
        // </summary>
        internal void AddNamespaceImport(MetadataNamespace @namespace, ErrorContext errCtx)
        {
            if (_namespaces.Contains(@namespace))
            {
                var message = Strings.NamespaceAlreadyImported(@namespace.Name);
                throw EntitySqlException.Create(errCtx, message, null);
            }

            _namespaces.Add(@namespace);
        }
示例#19
0
        // <summary>
        // Adds an aliased namespace import.
        // </summary>
        internal void AddAliasedNamespaceImport(string alias, MetadataNamespace @namespace, ErrorContext errCtx)
        {
            if (_aliasedNamespaces.ContainsKey(alias))
            {
                var message = Strings.NamespaceAliasAlreadyUsed(alias);
                throw EntitySqlException.Create(errCtx, message, null);
            }

            _aliasedNamespaces.Add(alias, @namespace);
        }
示例#20
0
        /// <summary>
        ///     Converts boolean literal value.
        /// </summary>
        private static bool ConvertBooleanLiteralValue(ErrorContext errCtx, string booleanLiteralValue)
        {
            var result = false;

            if (!Boolean.TryParse(booleanLiteralValue, out result))
            {
                var message = Strings.InvalidLiteralFormat("Boolean", booleanLiteralValue);
                throw EntitySqlException.Create(errCtx, message, null);
            }
            return(result);
        }
        private static bool ConvertBooleanLiteralValue(ErrorContext errCtx, string booleanLiteralValue)
        {
            bool result = false;

            if (!bool.TryParse(booleanLiteralValue, out result))
            {
                string errorMessage = Strings.InvalidLiteralFormat((object)"Boolean", (object)booleanLiteralValue);
                throw EntitySqlException.Create(errCtx, errorMessage, (Exception)null);
            }
            return(result);
        }
示例#22
0
 internal void AddAliasedNamespaceImport(
     string alias,
     MetadataNamespace @namespace,
     ErrorContext errCtx)
 {
     if (this._aliasedNamespaces.ContainsKey(alias))
     {
         string errorMessage = Strings.NamespaceAliasAlreadyUsed((object)alias);
         throw EntitySqlException.Create(errCtx, errorMessage, (Exception)null);
     }
     this._aliasedNamespaces.Add(alias, @namespace);
 }
示例#23
0
 private static System.Data.Entity.Core.Common.EntitySql.AST.Node Parse(
     string commandText,
     ParserOptions parserOptions)
 {
     Check.NotEmpty(commandText, nameof(commandText));
     System.Data.Entity.Core.Common.EntitySql.AST.Node node = new CqlParser(parserOptions, true).Parse(commandText);
     if (node == null)
     {
         throw EntitySqlException.Create(commandText, Strings.InvalidEmptyQuery, 0, (string)null, false, (Exception)null);
     }
     return(node);
 }
        internal NamespaceImport(BuiltInExpr bltInExpr)
        {
            this._namespaceAlias = (Identifier)null;
            Identifier identifier = bltInExpr.Arg1 as Identifier;

            if (identifier == null)
            {
                throw EntitySqlException.Create(bltInExpr.Arg1.ErrCtx, Strings.InvalidNamespaceAlias, (Exception)null);
            }
            this._namespaceAlias = identifier;
            this._namespaceName  = bltInExpr.Arg2;
        }
示例#25
0
 // <summary>
 // Maps operator to respective token
 // </summary>
 // <param name="oper"> operator lexeme </param>
 // <returns> Token </returns>
 internal Token MapOperator(string oper)
 {
     if (InternalOperatorDictionary.ContainsKey(oper))
     {
         return(NewToken(InternalOperatorDictionary[oper], new TerminalToken(oper, _iPos)));
     }
     else
     {
         var errorMessage = Strings.InvalidOperatorSymbol;
         throw EntitySqlException.Create(_query, errorMessage, _iPos, null, false, null);
     }
 }
示例#26
0
        // <summary>
        // Reports incompatible type error
        // </summary>
        internal static void ReportIncompatibleCommonType(ErrorContext errCtx, TypeUsage leftType, TypeUsage rightType)
        {
            //
            // 'navigate' through the type structure in order to find where the incompability is
            //
            ReportIncompatibleCommonType(errCtx, leftType, rightType, leftType, rightType);

            //
            // if we hit this point, throw the generic incompatible type error message
            //
            throw EntitySqlException.Create(errCtx, Strings.ArgumentTypesAreIncompatible(leftType.Identity, rightType.Identity), null);
        }
示例#27
0
        private static DateTimeOffset ConvertDateTimeOffsetLiteralValue(ErrorContext errCtx, string datetimeLiteralValue)
        {
            var datetimeParts = datetimeLiteralValue.Split(_datetimeOffsetSeparators, StringSplitOptions.RemoveEmptyEntries);

            Debug.Assert(datetimeParts.Length >= 7, "datetime literal value must have at least 7 parts");

            int year;
            int month;
            int day;

            GetDateParts(datetimeLiteralValue, datetimeParts, out year, out month, out day);
            int hour;
            int minute;
            int second;
            int ticks;
            //Copy the time parts into a different array since the last two parts will be handled in this method.
            var timeParts = new String[datetimeParts.Length - 2];

            Array.Copy(datetimeParts, timeParts, datetimeParts.Length - 2);
            GetTimeParts(datetimeLiteralValue, timeParts, 3, out hour, out minute, out second, out ticks);

            Debug.Assert(year >= 1 && year <= 9999);
            Debug.Assert(month >= 1 && month <= 12);
            Debug.Assert(day >= 1 && day <= 31);
            Debug.Assert(hour >= 0 && hour <= 24);
            Debug.Assert(minute >= 0 && minute <= 59);
            Debug.Assert(second >= 0 && second <= 59);
            Debug.Assert(ticks >= 0 && ticks <= 9999999);
            var offsetHours    = Int32.Parse(datetimeParts[datetimeParts.Length - 2], NumberStyles.Integer, CultureInfo.InvariantCulture);
            var offsetMinutes  = Int32.Parse(datetimeParts[datetimeParts.Length - 1], NumberStyles.Integer, CultureInfo.InvariantCulture);
            var offsetTimeSpan = new TimeSpan(offsetHours, offsetMinutes, 0);

            //If DateTimeOffset had a negative offset, we should negate the timespan
            if (datetimeLiteralValue.IndexOf('+')
                == -1)
            {
                offsetTimeSpan = offsetTimeSpan.Negate();
            }
            var dateTime = new DateTime(year, month, day, hour, minute, second, 0);

            dateTime = dateTime.AddTicks(ticks);

            try
            {
                return(new DateTimeOffset(dateTime, offsetTimeSpan));
            }
            catch (ArgumentOutOfRangeException e)
            {
                var message = Strings.InvalidDateTimeOffsetLiteral(datetimeLiteralValue);
                throw EntitySqlException.Create(errCtx, message, e);
            }
        }
        /// <summary>
        ///     Resolve entity set or function import <paramref name="name" /> in the <paramref name="entityContainer" />
        /// </summary>
        internal ExpressionResolution ResolveEntityContainerMemberAccess(EntityContainer entityContainer, string name, ErrorContext errCtx)
        {
            ExpressionResolution resolution;

            if (TryResolveEntityContainerMemberAccess(entityContainer, name, out resolution))
            {
                return(resolution);
            }
            else
            {
                var message = Strings.MemberDoesNotBelongToEntityContainer(name, entityContainer.Name);
                throw EntitySqlException.Create(errCtx, message, null);
            }
        }
        private void yyerror(string s)
        {
            if (s.Equals(_internalYaccSyntaxErrorMessage, StringComparison.Ordinal))
            {
                var    errorPosition     = _lexer.IPos;
                string syntaxContextInfo = null;
                var    term = _lexer.YYText;
                if (!String.IsNullOrEmpty(term))
                {
                    syntaxContextInfo = Strings.LocalizedTerm;
                    ErrorContext errCtx  = null;
                    var          astNode = yylval as Node;
                    if (null != astNode &&
                        (null != astNode.ErrCtx) &&
                        (!String.IsNullOrEmpty(astNode.ErrCtx.ErrorContextInfo)))
                    {
                        errCtx        = astNode.ErrCtx;
                        errorPosition = Math.Min(errorPosition, errorPosition - term.Length);
                    }

                    if ((yylval is CqlLexer.TerminalToken) &&
                        CqlLexer.IsReservedKeyword(term) &&
                        !(astNode is Identifier))
                    {
                        syntaxContextInfo = Strings.LocalizedKeyword;
                        term          = term.ToUpperInvariant();
                        errorPosition = Math.Min(errorPosition, errorPosition - term.Length);
                    }
                    else if (null != errCtx)
                    {
                        syntaxContextInfo = EntityRes.GetString(errCtx.ErrorContextInfo);
                    }

                    syntaxContextInfo = String.Format(CultureInfo.CurrentCulture, "{0} '{1}'", syntaxContextInfo, term);
                }

                var errorMessage = Strings.GenericSyntaxError;
                throw EntitySqlException.Create(
                          _query,
                          errorMessage,
                          errorPosition,
                          syntaxContextInfo,
                          false,
                          null);
            }
            var errorPosition1 = _lexer.IPos;

            throw EntitySqlException.Create(_query, s, errorPosition1, null, false, null);
        }
示例#30
0
        // <summary>
        // Constructs an aliased expression node.
        // </summary>
        internal AliasedExpr(Node expr, Identifier alias)
        {
            DebugCheck.NotNull(expr);
            DebugCheck.NotNull(alias);

            if (String.IsNullOrEmpty(alias.Name))
            {
                var errCtx  = alias.ErrCtx;
                var message = Strings.InvalidEmptyIdentifier;
                throw EntitySqlException.Create(errCtx, message, null);
            }

            _expr  = expr;
            _alias = alias;
        }