コード例 #1
0
        //
        // Returns true if the body of lambda expression can be implicitly
        // converted to the delegate of type `delegate_type'
        //
        public bool ImplicitStandardConversionExists(ParseContext ec, Type delegateType)
        {
            var expressionTreeConversion = false;

            if (!TypeManager.IsDelegateType(delegateType))
            {
                if (TypeManager.DropGenericTypeArguments(delegateType) != TypeManager.CoreTypes.GenericExpression)
                {
                    return(false);
                }

                delegateType             = delegateType.GetGenericArguments()[0];
                expressionTreeConversion = true;
            }

            var invokeMethod = delegateType.GetMethod("Invoke");        // TypeManager.GetDelegateInvokeMethod(ec, null, delegateType);
            var returnType   = invokeMethod.ReturnType;

            if (returnType.IsGenericParameter)
            {
                var genericArguments = delegateType.GetGenericArguments();
                returnType = genericArguments[returnType.GenericParameterPosition];
            }

            EnsureScope(ec);

            var delegateParameters = invokeMethod.GetParameters();

            if (delegateParameters.Length != _scope.Parameters.Count)
            {
                return(false);
            }

            var lambdaParameters = ResolveParameters(ec, null, delegateType);

            int i      = 0;
            var result = delegateParameters.All(delegateParameter => TypeUtils.AreAssignable(delegateParameter.ParameterType, lambdaParameters[i++].ParameterType));

            if (result)
            {
                var oldScope = ec.CurrentScope;
                ec.CurrentScope = _scope;
                var resolvedBody = _body.Resolve(ec);
                ec.CurrentScope = oldScope;

                if (!TypeUtils.AreAssignable(returnType, resolvedBody.Type))
                {
                    return(false);
                }

                _body         = resolvedBody;
                _resolvedBody = (expressionTreeConversion) ? new QuoteExpression(this) : resolvedBody;

                Type       = _body.Type;
                LambdaType = delegateType;
            }

            return(result);
        }
コード例 #2
0
        /// <summary>
        /// Checks the two types are assignable.
        /// </summary>
        /// <param name="memberInfo">The member info.</param>
        /// <param name="sourceValue">The source value.</param>
        /// <param name="destination">The destination.</param>
        /// <exception cref="ReflectionHelperException">thrown when types are not assignable.</exception>
        internal static void CheckAreAssignable(MemberInfo memberInfo, object sourceValue, Type destination)
        {
            Type source = TypeUtils.GetType(sourceValue);

            if (!destination.IsValueType && sourceValue == null)
            {
                return;
            }

            if (!TypeUtils.AreAssignable(source, destination))
            {
                throw new ReflectionHelperException(string.Format(CultureInfo.CurrentCulture, Strings.ReflectionHelper_Parameter_type_cannot_be_used_for_method, source, destination, memberInfo));
            }
        }