4

i am trying to call an parameterized constructor from an expression instead of using the default ctor. this is the code that gets the constructor parameter(s):

ConstructorInfo ci = type.GetConstructor(BindingFlags.Instance | BindingFlags.Public, null, CallingConventions.HasThis, new[] { typeof(bool) }, new ParameterModifier[] { });
ParameterInfo[] paramsInfo = ci.GetParameters();

//create a single param of type object[]
ParameterExpression param = Expression.Parameter(typeof(bool), "il");

Expression[] argsExp = new Expression[paramsInfo.Length];

//pick each arg from the params array 
//and create a typed expression of them
for (int i = 0; i < paramsInfo.Length; i++)
{
    Expression index = Expression.Constant(i);
    Type paramType = paramsInfo[i].ParameterType;

    Expression paramAccessorExp = param;
    //Expression.ArrayIndex(param, index);

    Expression paramCastExp =
        Expression.Convert(paramAccessorExp, paramType);

    argsExp[i] = param;
}                  

NewExpression ci2 = Expression.New(ci, argsExp);

But if i try to compile the lambda expression i am getting the following error:

variable 'il' of type 'System.Boolean' referenced from scope '', but it is not defined"

What am i missing? Any help and/ or hint is appreciated.

1
  • thank you both, i will try your suggestions tomorrow an let you know. Commented Nov 17, 2011 at 21:41

1 Answer 1

3

You define a parameter called li in the 4th line of your code. In order to use this in a lambda expression, you need to have a scope in which this parameter is defined. You have two choices:

  1. Create a BlockExpression that contains param as a local variable. Then use this expression as the body of your lambda expression.
  2. Use param as a parameter in your LambdaExpression.

If you use option 1, you'll also have to initialize the variable. Otherwise you'll get a different kind of error message.

EDIT

There are two problems with the additional code you posted:

  1. You need to use the same parameter object throughout your expression tree. Having the same name and type does not make two Parameter objects equal. I would simply move everything up to and including creating the lambda to the ConvertThis method so you can reuse the param variable. You can then just compile the return value of ConvertThis to get your delegate.

  2. When creating the BlockExpression, you need to pass param in as a local variable. You do this by adding an argument, new ParameterExpression[] { param } to the method.

Sign up to request clarification or add additional context in comments.

1 Comment

Hi Jeffrey, i'm trying your suggestion, but still have no idea. Please see my additions above.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.