Code:
/ 4.0 / 4.0 / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / fx / src / DLinq / Dlinq / SqlClient / Query / Funcletizer.cs / 1305376 / Funcletizer.cs
using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Linq; using System.Linq.Expressions; namespace System.Data.Linq.SqlClient { using System.Data.Linq.Mapping; using System.Diagnostics.CodeAnalysis; internal static class Funcletizer { internal static Expression Funcletize(Expression expression) { return new Localizer(new LocalMapper().MapLocals(expression)).Localize(expression); } class Localizer : ExpressionVisitor { Dictionarylocals; internal Localizer(Dictionary locals) { this.locals = locals; } internal Expression Localize(Expression expression) { return this.Visit(expression); } internal override Expression Visit(Expression exp) { if (exp == null) { return null; } if (this.locals.ContainsKey(exp)) { return MakeLocal(exp); } if (exp.NodeType == (ExpressionType)InternalExpressionType.Known) { return exp; } return base.Visit(exp); } private static Expression MakeLocal(Expression e) { if (e.NodeType == ExpressionType.Constant) { return e; } else if (e.NodeType == ExpressionType.Convert || e.NodeType == ExpressionType.ConvertChecked) { UnaryExpression ue = (UnaryExpression)e; if (ue.Type == typeof(object)) { Expression local = MakeLocal(ue.Operand); return (e.NodeType == ExpressionType.Convert) ? Expression.Convert(local, e.Type) : Expression.ConvertChecked(local, e.Type); } // convert a const null if (ue.Operand.NodeType == ExpressionType.Constant) { ConstantExpression c = (ConstantExpression)ue.Operand; if (c.Value == null) { return Expression.Constant(null, ue.Type); } } } return Expression.Invoke(Expression.Constant(Expression.Lambda(e).Compile())); } } class DependenceChecker : ExpressionVisitor { HashSet inScope = new HashSet (); bool isIndependent = true; /// /// This method returns 'true' when the expression doesn't reference any parameters /// from outside the scope of the expression. /// static public bool IsIndependent(Expression expression) { var v = new DependenceChecker(); v.Visit(expression); return v.isIndependent; } internal override Expression VisitLambda(LambdaExpression lambda) { foreach (var p in lambda.Parameters) { this.inScope.Add(p); } return base.VisitLambda(lambda); } internal override Expression VisitParameter(ParameterExpression p) { this.isIndependent &= this.inScope.Contains(p); return p; } } class LocalMapper : ExpressionVisitor { bool isRemote; Dictionarylocals; internal Dictionary MapLocals(Expression expression) { this.locals = new Dictionary (); this.isRemote = false; this.Visit(expression); return this.locals; } internal override Expression Visit(Expression expression) { if (expression == null) { return null; } bool saveIsRemote = this.isRemote; switch (expression.NodeType) { case (ExpressionType)InternalExpressionType.Known: return expression; case (ExpressionType)ExpressionType.Constant: break; default: this.isRemote = false; base.Visit(expression); if (!this.isRemote && expression.NodeType != ExpressionType.Lambda && expression.NodeType != ExpressionType.Quote && DependenceChecker.IsIndependent(expression)) { this.locals[expression] = true; // Not 'Add' because the same expression may exist in the tree twice. } break; } if (typeof(ITable).IsAssignableFrom(expression.Type) || typeof(DataContext).IsAssignableFrom(expression.Type)) { this.isRemote = true; } this.isRemote |= saveIsRemote; return expression; } internal override Expression VisitMemberAccess(MemberExpression m) { base.VisitMemberAccess(m); this.isRemote |= (m.Expression != null && typeof(ITable).IsAssignableFrom(m.Expression.Type)); return m; } internal override Expression VisitMethodCall(MethodCallExpression m) { base.VisitMethodCall(m); this.isRemote |= m.Method.DeclaringType == typeof(System.Data.Linq.Provider.DataManipulation) || Attribute.IsDefined(m.Method, typeof(FunctionAttribute)); return m; } } } internal abstract class ExpressionVisitor { internal ExpressionVisitor() { } [SuppressMessage("Microsoft.Maintainability", "CA1502:AvoidExcessiveComplexity", Justification = "These issues are related to our use of if-then and case statements for node types, which adds to the complexity count however when reviewed they are easy to navigate and understand.")] [SuppressMessage("Microsoft.Performance", "CA1800:DoNotCastUnnecessarily", Justification = "[....]: Cast is dependent on node type and casts do not happen unecessarily in a single code path.")] internal virtual Expression Visit(Expression exp) { if (exp == null) return exp; switch (exp.NodeType) { case ExpressionType.Negate: case ExpressionType.NegateChecked: case ExpressionType.Not: case ExpressionType.Convert: case ExpressionType.ConvertChecked: case ExpressionType.ArrayLength: case ExpressionType.Quote: case ExpressionType.TypeAs: return this.VisitUnary((UnaryExpression)exp); case ExpressionType.Add: case ExpressionType.AddChecked: case ExpressionType.Subtract: case ExpressionType.SubtractChecked: case ExpressionType.Multiply: case ExpressionType.MultiplyChecked: case ExpressionType.Divide: case ExpressionType.Modulo: case ExpressionType.Power: case ExpressionType.And: case ExpressionType.AndAlso: case ExpressionType.Or: case ExpressionType.OrElse: case ExpressionType.LessThan: case ExpressionType.LessThanOrEqual: case ExpressionType.GreaterThan: case ExpressionType.GreaterThanOrEqual: case ExpressionType.Equal: case ExpressionType.NotEqual: case ExpressionType.Coalesce: case ExpressionType.ArrayIndex: case ExpressionType.RightShift: case ExpressionType.LeftShift: case ExpressionType.ExclusiveOr: return this.VisitBinary((BinaryExpression)exp); case ExpressionType.TypeIs: return this.VisitTypeIs((TypeBinaryExpression)exp); case ExpressionType.Conditional: return this.VisitConditional((ConditionalExpression)exp); case ExpressionType.Constant: return this.VisitConstant((ConstantExpression)exp); case ExpressionType.Parameter: return this.VisitParameter((ParameterExpression)exp); case ExpressionType.MemberAccess: return this.VisitMemberAccess((MemberExpression)exp); case ExpressionType.Call: return this.VisitMethodCall((MethodCallExpression)exp); case ExpressionType.Lambda: return this.VisitLambda((LambdaExpression)exp); case ExpressionType.New: return this.VisitNew((NewExpression)exp); case ExpressionType.NewArrayInit: case ExpressionType.NewArrayBounds: return this.VisitNewArray((NewArrayExpression)exp); case ExpressionType.Invoke: return this.VisitInvocation((InvocationExpression)exp); case ExpressionType.MemberInit: return this.VisitMemberInit((MemberInitExpression)exp); case ExpressionType.ListInit: return this.VisitListInit((ListInitExpression)exp); case ExpressionType.UnaryPlus: if (exp.Type == typeof(TimeSpan)) return this.VisitUnary((UnaryExpression)exp); throw Error.UnhandledExpressionType(exp.NodeType); default: throw Error.UnhandledExpressionType(exp.NodeType); } } internal virtual MemberBinding VisitBinding(MemberBinding binding) { switch (binding.BindingType) { case MemberBindingType.Assignment: return this.VisitMemberAssignment((MemberAssignment)binding); case MemberBindingType.MemberBinding: return this.VisitMemberMemberBinding((MemberMemberBinding)binding); case MemberBindingType.ListBinding: return this.VisitMemberListBinding((MemberListBinding)binding); default: throw Error.UnhandledBindingType(binding.BindingType); } } internal virtual ElementInit VisitElementInitializer(ElementInit initializer) { ReadOnlyCollection arguments = this.VisitExpressionList(initializer.Arguments); if (arguments != initializer.Arguments) { return Expression.ElementInit(initializer.AddMethod, arguments); } return initializer; } internal virtual Expression VisitUnary(UnaryExpression u) { Expression operand = this.Visit(u.Operand); if (operand != u.Operand) { return Expression.MakeUnary(u.NodeType, operand, u.Type, u.Method); } return u; } internal virtual Expression VisitBinary(BinaryExpression b) { Expression left = this.Visit(b.Left); Expression right = this.Visit(b.Right); if (left != b.Left || right != b.Right) { return Expression.MakeBinary(b.NodeType, left, right, b.IsLiftedToNull, b.Method); } return b; } internal virtual Expression VisitTypeIs(TypeBinaryExpression b) { Expression expr = this.Visit(b.Expression); if (expr != b.Expression) { return Expression.TypeIs(expr, b.TypeOperand); } return b; } internal virtual Expression VisitConstant(ConstantExpression c) { return c; } internal virtual Expression VisitConditional(ConditionalExpression c) { Expression test = this.Visit(c.Test); Expression ifTrue = this.Visit(c.IfTrue); Expression ifFalse = this.Visit(c.IfFalse); if (test != c.Test || ifTrue != c.IfTrue || ifFalse != c.IfFalse) { return Expression.Condition(test, ifTrue, ifFalse); } return c; } internal virtual Expression VisitParameter(ParameterExpression p) { return p; } internal virtual Expression VisitMemberAccess(MemberExpression m) { Expression exp = this.Visit(m.Expression); if (exp != m.Expression) { return Expression.MakeMemberAccess(exp, m.Member); } return m; } internal virtual Expression VisitMethodCall(MethodCallExpression m) { Expression obj = this.Visit(m.Object); IEnumerable args = this.VisitExpressionList(m.Arguments); if (obj != m.Object || args != m.Arguments) { return Expression.Call(obj, m.Method, args); } return m; } internal virtual ReadOnlyCollection VisitExpressionList(ReadOnlyCollection original) { List list = null; for (int i = 0, n = original.Count; i < n; i++) { Expression p = this.Visit(original[i]); if (list != null) { list.Add(p); } else if (p != original[i]) { list = new List (n); for (int j = 0; j < i; j++) { list.Add(original[j]); } list.Add(p); } } if (list != null) return new ReadOnlyCollection (list); return original; } internal virtual MemberAssignment VisitMemberAssignment(MemberAssignment assignment) { Expression e = this.Visit(assignment.Expression); if (e != assignment.Expression) { return Expression.Bind(assignment.Member, e); } return assignment; } internal virtual MemberMemberBinding VisitMemberMemberBinding(MemberMemberBinding binding) { IEnumerable bindings = this.VisitBindingList(binding.Bindings); if (bindings != binding.Bindings) { return Expression.MemberBind(binding.Member, bindings); } return binding; } internal virtual MemberListBinding VisitMemberListBinding(MemberListBinding binding) { IEnumerable initializers = this.VisitElementInitializerList(binding.Initializers); if (initializers != binding.Initializers) { return Expression.ListBind(binding.Member, initializers); } return binding; } internal virtual IEnumerable VisitBindingList(ReadOnlyCollection original) { List list = null; for (int i = 0, n = original.Count; i < n; i++) { MemberBinding b = this.VisitBinding(original[i]); if (list != null) { list.Add(b); } else if (b != original[i]) { list = new List (n); for (int j = 0; j < i; j++) { list.Add(original[j]); } list.Add(b); } } if (list != null) return list; return original; } internal virtual IEnumerable VisitElementInitializerList(ReadOnlyCollection original) { List list = null; for (int i = 0, n = original.Count; i < n; i++) { ElementInit init = this.VisitElementInitializer(original[i]); if (list != null) { list.Add(init); } else if (init != original[i]) { list = new List (n); for (int j = 0; j < i; j++) { list.Add(original[j]); } list.Add(init); } } if (list != null) { return list; } return original; } internal virtual Expression VisitLambda(LambdaExpression lambda) { Expression body = this.Visit(lambda.Body); if (body != lambda.Body) { return Expression.Lambda(lambda.Type, body, lambda.Parameters); } return lambda; } internal virtual NewExpression VisitNew(NewExpression nex) { IEnumerable args = this.VisitExpressionList(nex.Arguments); if (args != nex.Arguments) { if (nex.Members != null) { return Expression.New(nex.Constructor, args, nex.Members); } else { return Expression.New(nex.Constructor, args); } } return nex; } internal virtual Expression VisitMemberInit(MemberInitExpression init) { NewExpression n = this.VisitNew(init.NewExpression); IEnumerable bindings = this.VisitBindingList(init.Bindings); if (n != init.NewExpression || bindings != init.Bindings) { return Expression.MemberInit(n, bindings); } return init; } internal virtual Expression VisitListInit(ListInitExpression init) { NewExpression n = this.VisitNew(init.NewExpression); IEnumerable initializers = this.VisitElementInitializerList(init.Initializers); if (n != init.NewExpression || initializers != init.Initializers) { return Expression.ListInit(n, initializers); } return init; } internal virtual Expression VisitNewArray(NewArrayExpression na) { IEnumerable exprs = this.VisitExpressionList(na.Expressions); if (exprs != na.Expressions) { if (na.NodeType == ExpressionType.NewArrayInit) { return Expression.NewArrayInit(na.Type.GetElementType(), exprs); } else { return Expression.NewArrayBounds(na.Type.GetElementType(), exprs); } } return na; } internal virtual Expression VisitInvocation(InvocationExpression iv) { IEnumerable args = this.VisitExpressionList(iv.Arguments); Expression expr = this.Visit(iv.Expression); if (args != iv.Arguments || expr != iv.Expression) { return Expression.Invoke(expr, args); } return iv; } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved. using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Linq; using System.Linq.Expressions; namespace System.Data.Linq.SqlClient { using System.Data.Linq.Mapping; using System.Diagnostics.CodeAnalysis; internal static class Funcletizer { internal static Expression Funcletize(Expression expression) { return new Localizer(new LocalMapper().MapLocals(expression)).Localize(expression); } class Localizer : ExpressionVisitor { Dictionary locals; internal Localizer(Dictionary locals) { this.locals = locals; } internal Expression Localize(Expression expression) { return this.Visit(expression); } internal override Expression Visit(Expression exp) { if (exp == null) { return null; } if (this.locals.ContainsKey(exp)) { return MakeLocal(exp); } if (exp.NodeType == (ExpressionType)InternalExpressionType.Known) { return exp; } return base.Visit(exp); } private static Expression MakeLocal(Expression e) { if (e.NodeType == ExpressionType.Constant) { return e; } else if (e.NodeType == ExpressionType.Convert || e.NodeType == ExpressionType.ConvertChecked) { UnaryExpression ue = (UnaryExpression)e; if (ue.Type == typeof(object)) { Expression local = MakeLocal(ue.Operand); return (e.NodeType == ExpressionType.Convert) ? Expression.Convert(local, e.Type) : Expression.ConvertChecked(local, e.Type); } // convert a const null if (ue.Operand.NodeType == ExpressionType.Constant) { ConstantExpression c = (ConstantExpression)ue.Operand; if (c.Value == null) { return Expression.Constant(null, ue.Type); } } } return Expression.Invoke(Expression.Constant(Expression.Lambda(e).Compile())); } } class DependenceChecker : ExpressionVisitor { HashSet inScope = new HashSet (); bool isIndependent = true; /// /// This method returns 'true' when the expression doesn't reference any parameters /// from outside the scope of the expression. /// static public bool IsIndependent(Expression expression) { var v = new DependenceChecker(); v.Visit(expression); return v.isIndependent; } internal override Expression VisitLambda(LambdaExpression lambda) { foreach (var p in lambda.Parameters) { this.inScope.Add(p); } return base.VisitLambda(lambda); } internal override Expression VisitParameter(ParameterExpression p) { this.isIndependent &= this.inScope.Contains(p); return p; } } class LocalMapper : ExpressionVisitor { bool isRemote; Dictionarylocals; internal Dictionary MapLocals(Expression expression) { this.locals = new Dictionary (); this.isRemote = false; this.Visit(expression); return this.locals; } internal override Expression Visit(Expression expression) { if (expression == null) { return null; } bool saveIsRemote = this.isRemote; switch (expression.NodeType) { case (ExpressionType)InternalExpressionType.Known: return expression; case (ExpressionType)ExpressionType.Constant: break; default: this.isRemote = false; base.Visit(expression); if (!this.isRemote && expression.NodeType != ExpressionType.Lambda && expression.NodeType != ExpressionType.Quote && DependenceChecker.IsIndependent(expression)) { this.locals[expression] = true; // Not 'Add' because the same expression may exist in the tree twice. } break; } if (typeof(ITable).IsAssignableFrom(expression.Type) || typeof(DataContext).IsAssignableFrom(expression.Type)) { this.isRemote = true; } this.isRemote |= saveIsRemote; return expression; } internal override Expression VisitMemberAccess(MemberExpression m) { base.VisitMemberAccess(m); this.isRemote |= (m.Expression != null && typeof(ITable).IsAssignableFrom(m.Expression.Type)); return m; } internal override Expression VisitMethodCall(MethodCallExpression m) { base.VisitMethodCall(m); this.isRemote |= m.Method.DeclaringType == typeof(System.Data.Linq.Provider.DataManipulation) || Attribute.IsDefined(m.Method, typeof(FunctionAttribute)); return m; } } } internal abstract class ExpressionVisitor { internal ExpressionVisitor() { } [SuppressMessage("Microsoft.Maintainability", "CA1502:AvoidExcessiveComplexity", Justification = "These issues are related to our use of if-then and case statements for node types, which adds to the complexity count however when reviewed they are easy to navigate and understand.")] [SuppressMessage("Microsoft.Performance", "CA1800:DoNotCastUnnecessarily", Justification = "[....]: Cast is dependent on node type and casts do not happen unecessarily in a single code path.")] internal virtual Expression Visit(Expression exp) { if (exp == null) return exp; switch (exp.NodeType) { case ExpressionType.Negate: case ExpressionType.NegateChecked: case ExpressionType.Not: case ExpressionType.Convert: case ExpressionType.ConvertChecked: case ExpressionType.ArrayLength: case ExpressionType.Quote: case ExpressionType.TypeAs: return this.VisitUnary((UnaryExpression)exp); case ExpressionType.Add: case ExpressionType.AddChecked: case ExpressionType.Subtract: case ExpressionType.SubtractChecked: case ExpressionType.Multiply: case ExpressionType.MultiplyChecked: case ExpressionType.Divide: case ExpressionType.Modulo: case ExpressionType.Power: case ExpressionType.And: case ExpressionType.AndAlso: case ExpressionType.Or: case ExpressionType.OrElse: case ExpressionType.LessThan: case ExpressionType.LessThanOrEqual: case ExpressionType.GreaterThan: case ExpressionType.GreaterThanOrEqual: case ExpressionType.Equal: case ExpressionType.NotEqual: case ExpressionType.Coalesce: case ExpressionType.ArrayIndex: case ExpressionType.RightShift: case ExpressionType.LeftShift: case ExpressionType.ExclusiveOr: return this.VisitBinary((BinaryExpression)exp); case ExpressionType.TypeIs: return this.VisitTypeIs((TypeBinaryExpression)exp); case ExpressionType.Conditional: return this.VisitConditional((ConditionalExpression)exp); case ExpressionType.Constant: return this.VisitConstant((ConstantExpression)exp); case ExpressionType.Parameter: return this.VisitParameter((ParameterExpression)exp); case ExpressionType.MemberAccess: return this.VisitMemberAccess((MemberExpression)exp); case ExpressionType.Call: return this.VisitMethodCall((MethodCallExpression)exp); case ExpressionType.Lambda: return this.VisitLambda((LambdaExpression)exp); case ExpressionType.New: return this.VisitNew((NewExpression)exp); case ExpressionType.NewArrayInit: case ExpressionType.NewArrayBounds: return this.VisitNewArray((NewArrayExpression)exp); case ExpressionType.Invoke: return this.VisitInvocation((InvocationExpression)exp); case ExpressionType.MemberInit: return this.VisitMemberInit((MemberInitExpression)exp); case ExpressionType.ListInit: return this.VisitListInit((ListInitExpression)exp); case ExpressionType.UnaryPlus: if (exp.Type == typeof(TimeSpan)) return this.VisitUnary((UnaryExpression)exp); throw Error.UnhandledExpressionType(exp.NodeType); default: throw Error.UnhandledExpressionType(exp.NodeType); } } internal virtual MemberBinding VisitBinding(MemberBinding binding) { switch (binding.BindingType) { case MemberBindingType.Assignment: return this.VisitMemberAssignment((MemberAssignment)binding); case MemberBindingType.MemberBinding: return this.VisitMemberMemberBinding((MemberMemberBinding)binding); case MemberBindingType.ListBinding: return this.VisitMemberListBinding((MemberListBinding)binding); default: throw Error.UnhandledBindingType(binding.BindingType); } } internal virtual ElementInit VisitElementInitializer(ElementInit initializer) { ReadOnlyCollection arguments = this.VisitExpressionList(initializer.Arguments); if (arguments != initializer.Arguments) { return Expression.ElementInit(initializer.AddMethod, arguments); } return initializer; } internal virtual Expression VisitUnary(UnaryExpression u) { Expression operand = this.Visit(u.Operand); if (operand != u.Operand) { return Expression.MakeUnary(u.NodeType, operand, u.Type, u.Method); } return u; } internal virtual Expression VisitBinary(BinaryExpression b) { Expression left = this.Visit(b.Left); Expression right = this.Visit(b.Right); if (left != b.Left || right != b.Right) { return Expression.MakeBinary(b.NodeType, left, right, b.IsLiftedToNull, b.Method); } return b; } internal virtual Expression VisitTypeIs(TypeBinaryExpression b) { Expression expr = this.Visit(b.Expression); if (expr != b.Expression) { return Expression.TypeIs(expr, b.TypeOperand); } return b; } internal virtual Expression VisitConstant(ConstantExpression c) { return c; } internal virtual Expression VisitConditional(ConditionalExpression c) { Expression test = this.Visit(c.Test); Expression ifTrue = this.Visit(c.IfTrue); Expression ifFalse = this.Visit(c.IfFalse); if (test != c.Test || ifTrue != c.IfTrue || ifFalse != c.IfFalse) { return Expression.Condition(test, ifTrue, ifFalse); } return c; } internal virtual Expression VisitParameter(ParameterExpression p) { return p; } internal virtual Expression VisitMemberAccess(MemberExpression m) { Expression exp = this.Visit(m.Expression); if (exp != m.Expression) { return Expression.MakeMemberAccess(exp, m.Member); } return m; } internal virtual Expression VisitMethodCall(MethodCallExpression m) { Expression obj = this.Visit(m.Object); IEnumerable args = this.VisitExpressionList(m.Arguments); if (obj != m.Object || args != m.Arguments) { return Expression.Call(obj, m.Method, args); } return m; } internal virtual ReadOnlyCollection VisitExpressionList(ReadOnlyCollection original) { List list = null; for (int i = 0, n = original.Count; i < n; i++) { Expression p = this.Visit(original[i]); if (list != null) { list.Add(p); } else if (p != original[i]) { list = new List (n); for (int j = 0; j < i; j++) { list.Add(original[j]); } list.Add(p); } } if (list != null) return new ReadOnlyCollection (list); return original; } internal virtual MemberAssignment VisitMemberAssignment(MemberAssignment assignment) { Expression e = this.Visit(assignment.Expression); if (e != assignment.Expression) { return Expression.Bind(assignment.Member, e); } return assignment; } internal virtual MemberMemberBinding VisitMemberMemberBinding(MemberMemberBinding binding) { IEnumerable bindings = this.VisitBindingList(binding.Bindings); if (bindings != binding.Bindings) { return Expression.MemberBind(binding.Member, bindings); } return binding; } internal virtual MemberListBinding VisitMemberListBinding(MemberListBinding binding) { IEnumerable initializers = this.VisitElementInitializerList(binding.Initializers); if (initializers != binding.Initializers) { return Expression.ListBind(binding.Member, initializers); } return binding; } internal virtual IEnumerable VisitBindingList(ReadOnlyCollection original) { List list = null; for (int i = 0, n = original.Count; i < n; i++) { MemberBinding b = this.VisitBinding(original[i]); if (list != null) { list.Add(b); } else if (b != original[i]) { list = new List (n); for (int j = 0; j < i; j++) { list.Add(original[j]); } list.Add(b); } } if (list != null) return list; return original; } internal virtual IEnumerable VisitElementInitializerList(ReadOnlyCollection original) { List list = null; for (int i = 0, n = original.Count; i < n; i++) { ElementInit init = this.VisitElementInitializer(original[i]); if (list != null) { list.Add(init); } else if (init != original[i]) { list = new List (n); for (int j = 0; j < i; j++) { list.Add(original[j]); } list.Add(init); } } if (list != null) { return list; } return original; } internal virtual Expression VisitLambda(LambdaExpression lambda) { Expression body = this.Visit(lambda.Body); if (body != lambda.Body) { return Expression.Lambda(lambda.Type, body, lambda.Parameters); } return lambda; } internal virtual NewExpression VisitNew(NewExpression nex) { IEnumerable args = this.VisitExpressionList(nex.Arguments); if (args != nex.Arguments) { if (nex.Members != null) { return Expression.New(nex.Constructor, args, nex.Members); } else { return Expression.New(nex.Constructor, args); } } return nex; } internal virtual Expression VisitMemberInit(MemberInitExpression init) { NewExpression n = this.VisitNew(init.NewExpression); IEnumerable bindings = this.VisitBindingList(init.Bindings); if (n != init.NewExpression || bindings != init.Bindings) { return Expression.MemberInit(n, bindings); } return init; } internal virtual Expression VisitListInit(ListInitExpression init) { NewExpression n = this.VisitNew(init.NewExpression); IEnumerable initializers = this.VisitElementInitializerList(init.Initializers); if (n != init.NewExpression || initializers != init.Initializers) { return Expression.ListInit(n, initializers); } return init; } internal virtual Expression VisitNewArray(NewArrayExpression na) { IEnumerable exprs = this.VisitExpressionList(na.Expressions); if (exprs != na.Expressions) { if (na.NodeType == ExpressionType.NewArrayInit) { return Expression.NewArrayInit(na.Type.GetElementType(), exprs); } else { return Expression.NewArrayBounds(na.Type.GetElementType(), exprs); } } return na; } internal virtual Expression VisitInvocation(InvocationExpression iv) { IEnumerable args = this.VisitExpressionList(iv.Arguments); Expression expr = this.Visit(iv.Expression); if (args != iv.Arguments || expr != iv.Expression) { return Expression.Invoke(expr, args); } return iv; } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- FormatConvertedBitmap.cs
- EventHandlerService.cs
- SoapParser.cs
- ContentHostHelper.cs
- DataGridViewDataConnection.cs
- ParseChildrenAsPropertiesAttribute.cs
- GridViewCommandEventArgs.cs
- SoapTypeAttribute.cs
- FlowLayoutSettings.cs
- CommandEventArgs.cs
- MatchingStyle.cs
- LabelAutomationPeer.cs
- HandleRef.cs
- CryptoStream.cs
- HasCopySemanticsAttribute.cs
- StringReader.cs
- ParentControlDesigner.cs
- TrackingMemoryStreamFactory.cs
- Panel.cs
- DataSourceListEditor.cs
- RegistryConfigurationProvider.cs
- CompareInfo.cs
- GridViewColumnCollectionChangedEventArgs.cs
- HtmlForm.cs
- Int32Converter.cs
- MetabaseServerConfig.cs
- SqlBuffer.cs
- CollectionEditVerbManager.cs
- ResourcePermissionBase.cs
- ViewValidator.cs
- AssertFilter.cs
- TextTreeRootTextBlock.cs
- C14NUtil.cs
- StandardOleMarshalObject.cs
- CallTemplateAction.cs
- WindowsAuthenticationModule.cs
- IdentityReference.cs
- XmlConverter.cs
- RegularExpressionValidator.cs
- PropertyDescriptorGridEntry.cs
- RevocationPoint.cs
- ThemeableAttribute.cs
- WriteableBitmap.cs
- URI.cs
- TransformGroup.cs
- WebProxyScriptElement.cs
- RelationshipManager.cs
- InnerItemCollectionView.cs
- MailSettingsSection.cs
- Wizard.cs
- ContainerVisual.cs
- DataGridSortCommandEventArgs.cs
- MetafileHeaderWmf.cs
- BaseCollection.cs
- CodeTypeMemberCollection.cs
- SessionStateSection.cs
- WindowsFormsHostAutomationPeer.cs
- ModulesEntry.cs
- DataSourceCollectionBase.cs
- FilteredAttributeCollection.cs
- TypedTableBaseExtensions.cs
- TextDecorationCollectionConverter.cs
- ConditionalWeakTable.cs
- IODescriptionAttribute.cs
- HttpCachePolicy.cs
- PropertyGridCommands.cs
- BuiltInPermissionSets.cs
- XmlReflectionImporter.cs
- ProfessionalColorTable.cs
- SafeFileMappingHandle.cs
- AutoGeneratedField.cs
- PageParserFilter.cs
- CodeExpressionStatement.cs
- ObjectListDataBindEventArgs.cs
- ResourcePool.cs
- LocalizableAttribute.cs
- Vector3DCollectionConverter.cs
- Matrix.cs
- ActivityWithResultWrapper.cs
- TextAnchor.cs
- UnsafeNativeMethodsTablet.cs
- BrushValueSerializer.cs
- FileUtil.cs
- AttributeEmitter.cs
- Compress.cs
- CodeAccessPermission.cs
- XPathBuilder.cs
- TouchEventArgs.cs
- SerializerDescriptor.cs
- ChtmlTextWriter.cs
- DragDrop.cs
- BaseTypeViewSchema.cs
- BasicViewGenerator.cs
- GridViewAutomationPeer.cs
- _NegoStream.cs
- XpsDocument.cs
- AssociationSetEnd.cs
- AsyncDataRequest.cs
- ResourceExpressionBuilder.cs
- FormatException.cs