views:

720

answers:

5

I want to preserve a property between postbacks in an ASP.Net application. Currently doing this:

    public int MyIndex
    {
        get
        {
            return (int)Session[ToString() + "MyIndex"];
        }
    }

but would prefer something like:

    public int MyIndex
    {
        get
        {
            return (int)Session[ToString() + #code_that_returns_property_name#];
        }
    }

Setter omitted, but it just pushes value into Session using the same string. Is there some way to use reflection, or a different better solution?

+3  A: 

No, there isn't a simple way to do what you want to do. I think you are much better off with the code you have already written.

Edit: This answer has received quite a few downvotes and I do understand why. While it is possible to do what the OP wants to do perhaps we should all stop and think whether or not it is advisable to do so. To paraphrase the immortal words of Dr. Ian Malcom, just because you can do something doesn't mean you should.

Andrew Hare
Why the down vote? it's the most sensible answer... :) +1 from me.
Paolo Tedesco
+1 from me as well, this is an INSANE idea. If you find you have to do it a lot, and the name keeps changing, so managing it becomes a burden, then use a .tt file to codegen the property declarations or something like that.
Daniel Earwicker
+7  A: 
public static int Dummy {
    get {
        var propertyName = MethodBase.GetCurrentMethod().Name.Substring(4);
        Console.WriteLine(propertyName);
        return 0;
    }
}
Simon Svensson
GetCurrentMethod() returned a System.ArgumentException for me...
Nope, it worked. Not sure where that exception came from. Works fine now. Just what I needed.
For the love of God, no! The result is five times longer and a 100 times more obscure than what it replaced! Unless you're going to be continually changing your mind about what to call that property, this is a ridiculous idea. (... IMHO)
Daniel Earwicker
In addition to the other comments, this method is going to be hundreds (thousands?) of times slower, reflection isn't cheap. It may not be a concern for the OP, but anyone considering something like this needs to be aware. (a simple test on my machine the reflection version took 71 seconds for 10000000 calls, the hard coded version took 0.8 seconds)
Dolphin
+3  A: 

You can use MethodInfo.GetCurrentMethod().Name to return the name of the current method:

public int MyIndex
{
    get
    {
        return (int)Session[ToString() + MethodInfo.GetCurrentMethod().Name];
    }
}

Since properties are implemented as methods under the hood, that will return a name like "get_MyIndex". If you don't want the "get_" part, you can substring out a few characters:

public int MyIndex
{
    get
    {
        return (int)Session[ToString() + MethodInfo.GetCurrentMethod().Name.Substring(4)];
    }
}
Judah Himango
+1  A: 

You should rather use the ViewState property of your control:

public int MyIndex {
    get { 
        object index = ViewState["MyIndex"];
        return (null == index) ? -1 : (int)index;
    }
    set {
        ViewState["MyIndex"] = value;
    }
}
Paolo Tedesco
+1  A: 

You can use an expression tree to get the member name. It's a bit of a hock but it works. Here is the code.

private string GetPropertyName<TValue>(Expression<Func<BindingSourceType, TValue>> propertySelector)
{
    var memberExpression = propertySelector.Body as MemberExpression;
    if (memberExpression != null)
    {
        return memberExpression.Member.Name;
    }
    else
    {
       return string.empty;    
    }
}

With that code you can do the following

return (int)Session[ToString() + GetPropertyName(MyIndex)];

Code ruthlessly stolen from Romain's answer on the following thread

JaredPar
What an elegant solution! +1
Paolo Tedesco
Cannot resolve symbol 'BindingSourceType'This is an ASP.Net 3.5 project...
If you read the original answer from the other thread, it says that BindingSourceType is the class name which contains the property. You need to use the name of the class that the property MyIndex belongs to.
adrianbanks