1

Consider following code:

public class Test
{
    [System.AttributeUsage(System.AttributeTargets.Method)]
    class MethodAttribute : System.Attribute
    {
        public MethodAttribute(System.Reflection.MethodInfo methodInfo)
        {

        }
    }

    public void Foo()
    {

    }

    [Method(Test.Foo)] //< THIS IS THE IMPORTANT LINE
    public void Boo()
    {

    }
}

I want to store MethodInfo instance of Foo in attribute of Boo, but problem is, that I cannot use Foo nor Test.Foo to get instance of MethodInfo. I can NOT use typeof(Test).GetMethod("Foo") (not my decision).

Important information:

Absolutely unimportant information:

  • Why I cannot use typeof(Test).GetMethod("Foo"): I'm not allowed. It's not in my power to change this decision. I can not. (Also, personally, I would like to avoid it anyway as it needs to do some lookup instead of getting statically the data. Also it won't be changed automatically during refactoring and will be checking run-time, not compile-time.)
  • Why I want to do this: later in code, I want to create a delegate of Boo() (this time normally, with an instance) and use in special even system or something. Before it's called, this attribute allows to setup method to be called in prepare for main event (it's optional, it can be null) and I know how to create a delegate when I have an object and a method info.
  • Why I cannot just provide both delegates when registering or something: because class containing these methods is not always the one who registers to event source, I need to keep the registration code as simple as possible. In other words, I want to avoid situation when person writing method responsible for connecting forgots to add this preparation delegate.
8
  • I'm not sure but I think that attributes can contain only compile constant values, so using reflection inside would not compile anyway. Commented Aug 27, 2014 at 6:57
  • Isn't pointer to MethodInfo constant? I mean, it's not Python, you cannot change pointer to method in a class. Only if it's virtual, but I want the particular Test.Foo MethodInfo and that should be unchanged whole time, am I wrong? I mean, you can't do something like Test.Foo = Test.Boo or Test.Foo = () => ... ;... Commented Aug 27, 2014 at 6:59
  • I think it is constant per app domain (may be wrong - can some confirm or decline?) - but in c# there is no way to get MethodInfo without using GetMethod, GetMethods or Expression tree. Commented Aug 27, 2014 at 7:03
  • Yea, its literally impossible to do what you want to do. Thats why you see attributes referencing methods as string names all the time, not b/c it's pretty but thats just all you can do. Commented Aug 27, 2014 at 7:05
  • That's sad, but what can I do. Thanks for the info! (Btw. interesting thing is that the code compiles just fine using .Net, but Unity3D is using Mono.) Commented Aug 27, 2014 at 7:08

1 Answer 1

0

use expression :

static public class Metadata<T>
{
    static public PropertyInfo Property<TProperty>(Expression<Func<T, TProperty>> property)
    {
        var expression = property.Body as MemberExpression;
        return expression.Member as PropertyInfo;
    }
}

var foo = Metadata<Test>.Property(test => test.Foo);
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

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