Speuline
Speuline

Reputation: 201

Get a List of property name with Lambda

I've this code:

    public string GetPropName<T1, T2>(Expression<Func<T1, T2>> expression)
    {
        var member = expression.Body as MemberExpression;
        if (member != null) return member.Member.Name;
        throw new ArgumentException();
    }

With it I can retrieve the name of a property with lamba:

string propName= GetPropName((MyObject o) => o.MyProperty);
// propName will be "MyProperty"

I want to achieve the same thing but the method should return a list of property name. For example:

List<string> PropNames= GetPropName((MyObject o) => o.MyProp, o.MySecondProp, o.EtcProp);
//PropNames will contains "MyProp", "MySecondProp", "EtcProp"

Do you think it's possible?

Thanks in advance

Edit:

p.s.w.g answer works well!

I've found another alternative:

public List<String> GetPropNames<T>(params Expression<Func<T, object>>[] navigationProperties)
{
    var result = new List<String>();
    foreach (var navigationProperty in navigationProperties)
    {
        var member = navigationProperty.Body as MemberExpression;
        if (member == null)
        {
            throw new ArgumentException();
        }
        result.Add(member.Member.Name);
    }
    return result;
}

Then I can call it this way:

List<String> MyProps= GetPropNames<MyObject>(e => e.MyFirstProp, e => e.MySecondProp,e=> MyEtcProp);

It works too. Thanks a lot!

Upvotes: 1

Views: 1943

Answers (2)

Mohsen Tarassoli
Mohsen Tarassoli

Reputation: 26

I just want to answer this **** question because I google it to find the syntax and this thread is always in top so I'm writing it basically for future me:

This is query way:

var listOfThePropertyUNeed = (from e in TheParentListUWantItFrom select e.thePropertyUWantToReturn).toArray();

This is lamda way:

var listOfThePropertyUNeed = employees.Select(e => e.thePropertyUWantToReturn).ToArray();

You can do whatever with those lists

Upvotes: 0

p.s.w.g
p.s.w.g

Reputation: 148990

I agree with Jon Skeet's comment: nameof is a better way to get arbitrary property names. But assuming that's absolutely not an option, here's one way to do it using expression trees:

public string[] GetPropNames<T1, T2>(Expression<Func<T1, T2>> expression)
{
    var newExp = expression.Body as NewExpression;
    if (newExp == null)
    {
        throw new ArgumentException();
    }

    var props = new List<string>(newExp.Arguments.Count);
    foreach (var argExp in newExp.Arguments)
    {
        var memberExp = argExp as MemberExpression;
        if (memberExp == null)
        {
            throw new ArgumentException();
        }
        props.Add(memberExp.Member.Name);
    }
    return props.ToArray();
}

Usage:

GetPropNames((MyObject o) => new { o.MyProp, o.MySecondProp, o.EtcProp })

This is pretty brittle, but it should demonstrate the general principle.

Upvotes: 4

Related Questions