tags:

views:

160

answers:

4

Hi,

i would like to know if it's possible to do something like this:

class brand
{
  string name;
}

class car
{
   string carname;
   brand carbrand;
}

now i've got a string like this and an instantiated object of the type car:

 car carobject = new car();
 string brandNameOfCar = DoSomeMagicalReflectionStuff(car, "car.brand.name");

How would the "DoSomeMagicalReflectionStuff" method look like?

And is it even possible to do something like:

 car carobject = new car();
 string brandNameOfCar = DoSomeMagicalReflectionStuff(car, "car.brand.name.ToFormatedString()");

Thank you!

+1  A: 

I usually don't try to plug products I'm involved in, but this is a perfect problem to be solved by Vici Parser (open source expression parser for .NET):

var parser = new CSharpParser();
var context = new CSharpContext();

context["car"] = carobject;

string brandNameOfCar = 
          parser.Evaluate<string>("car.brand.name.ToFormatedString()", context);
Philippe Leybaert
sounds good, thank you!
An overkill for something easily implemented with the bcl of .net if you ask me
Rune FS
@Rune: you don't really know the reasons why he wants something that evaluates expressions stored in a string. I personally use dynamic expression parsing a lot for creating very simple DSL solutions.
Philippe Leybaert
Big thanks again! The ViciParser is awesome :)
A: 

Typeof(car).GetProperty("brand", bindingflags.instance | bindingflags.private).GetValue(carobject,null) should so it. Sry for minor syntax errors bit im on my phone

edit: the above Will give you the brand object and you Can the dó the same to get to the name property

Rune FS
+4  A: 

I didn't test this, but here's something that should work:

car c = new car();
object val = typeof(car).GetField("carbrand", BindingFlags.Private).GetValue(c);
string result = (val as brand).ToFormattedString();
John Fisher
A: 

Would it make more sense to have a constructor of car that takes a string as a parameter and does something like the following:

class brand
{
    public string name;
}

class car
{

    public car(string s)
    {
        Match match = Regex.Match(s, @"(?<carname>[^\.]+)\.(?<brandname>.+)");
        if (match.Success)
        {
            this.carname = match.Groups["carname"].Value;
            this.carbrand = new brand();
            this.carbrand.name = match.Groups["brandname"].Value;
        } else
        {
            throw new ArgumentException("Not a valid car");
        }
    }

    string carname;
    brand carbrand;

    public override string ToString()
    {
        return carname + "." + carbrand.name;
    }
}

With the following use:

car c = new car("M5.BMW");
Console.WriteLine(c.ToString());

You could off course separate it into a Parse and TryParse method.

Yuriy Faktorovich
Wow, someone should take your keyboard holder licence away from you ! Why a string ? why parsing it ? why not 2 arguments ? o_O
Clement Herreman
Because the question was passing in a string, for example if it was parsing a file from somewhere which had many cars.
Yuriy Faktorovich
Although in your favor, the standard is to not have a constructor with a string like that, but a Parse method instead.
Yuriy Faktorovich