Exemple #1
0
        /// <summary>
        /// 访问字段或者属性表达式
        /// </summary>
        /// <param name="node">字段或者成员表达式</param>
        /// <returns></returns>
        protected override Expression VisitMember(MemberExpression node)
        {
            // 1.<>h__TransparentIdentifier3.b.Client.ClientName
            // 2.<>h__TransparentIdentifier3.b.Client.ClientName.Length
            // 3.<>h__TransparentIdentifier3.b.Client.Address.AddressName
            // 4.<>h__TransparentIdentifier3.b.ClientName
            // <>h__TransparentIdentifier2.<>h__TransparentIdentifier3.b.ClientName
            // <>h__TransparentIdentifier2.<>h__TransparentIdentifier3.b.Client.ClientName
            // <>h__TransparentIdentifier2.<>h__TransparentIdentifier3.b.Client.Address.AddressName
            // 5.b.ClientName


            if (node == null)
            {
                return(node);
            }
            // => a.ActiveDate == DateTime.Now  => a.State == (byte)state
            if (node.CanEvaluate())
            {
                return(this.VisitConstant(node.Evaluate()));
            }
            // => DateTime.Now
            if (node.Type == typeof(DateTime) && node.Expression == null)
            {
                return(this.VisitMethodCall(node, MethodCallType.MemberMember));
            }
            // => a.Nullable.Value
            bool isNullable = node.Expression.Type.IsGenericType && node.Member.Name == "Value" && node.Expression.Type.GetGenericTypeDefinition() == typeof(Nullable <>);

            if (isNullable)
            {
                this.Visit(node.Expression);
                return(node);
            }

            // 记录访问成员栈
            _visitedStack.Add(node);

            // => a.Name.Length
            if (TypeUtils.IsPrimitiveType(node.Expression.Type))
            {
                return(this.VisitMethodCall(node, MethodCallType.MemberMember));
            }
            // => <>h__3.b.ClientName
            if (!node.Expression.Visitable())
            {
                _builder.AppendMember(_ag, node);
                return(node);
            }
            // => a.Accounts[0].Markets[0].MarketId
            // => b.Client.Address.AddressName
            Expression objExpression = node.Expression;
            bool       isMethodCall  = objExpression != null && objExpression.NodeType == ExpressionType.Call;

            if (isMethodCall)
            {
                MethodCallExpression methodExpression = objExpression as MethodCallExpression;
                bool isIndex = methodExpression.IsCollectionIndex();
                if (isIndex)
                {
                    objExpression = methodExpression.Object;
                }
            }
            // => b.Client.Address.AddressName
            this.VisitNavMember(objExpression, TypeUtils.GetFieldName(node.Member, node.Expression.Type));

            return(node);
        }
        /// <summary>
        /// 判断表达式链是否能通过动态计算,计算出它的值
        /// </summary>
        public static bool CanEvaluate(this Expression node)
        {
            // => 5
            // => a.ActiveDate == DateTime.Now
            // => a.State == (byte)state
            // => a.Accounts[0].Markets[0].MarketId

            if (node == null)
            {
                return(false);
            }
            if (node.NodeType == ExpressionType.Constant)
            {
                return(true);
            }
            if (node.NodeType == ExpressionType.ArrayIndex)
            {
                return(true);
            }
            if (node.NodeType == ExpressionType.Call)
            {
                // List<int>{0}[]
                // => a.Accounts[0].Markets[0].MarketId
                MethodCallExpression methodExpression = node as MethodCallExpression;
                bool isIndex = methodExpression.IsCollectionIndex();
                if (isIndex)
                {
                    node = methodExpression.Object;
                }
            }

            if (node.NodeType == ExpressionType.ListInit)
            {
                return(true);
            }
            if (node.NodeType == ExpressionType.NewArrayInit)
            {
                return(true);
            }
            if (node.NodeType == ExpressionType.NewArrayBounds)
            {
                return(true);
            }
            if (node.NodeType != ExpressionType.MemberAccess)
            {
                return(false);
            }

            var memberExpression = node as MemberExpression;

            if (memberExpression == null)
            {
                return(false);
            }
            if (memberExpression.Expression == null)
            {
                // 排除 DateTime 的几个常量
                bool isDateTime = memberExpression.Type == typeof(DateTime) &&
                                  (memberExpression.Member.Name == "Now" || memberExpression.Member.Name == "UtcNow" || memberExpression.Member.Name == "Today");
                return(!isDateTime);
            }
            if (memberExpression.Expression.NodeType == ExpressionType.Constant)
            {
                return(true);
            }

            return(memberExpression.Expression.CanEvaluate());
        }