1

Is there any simple way to convert/parse many Objects of Class Foo to objects of class Bar, using a member method of class Bar like Bar.loadFromFooObject(Foo classFoo) ?

So if I have those 2 Classes:

class Foo
{
   public string var1;
   public int var2;
   public List<string> var3;
}

class Bar
{
   public string var1;
   public int var2;
   public float var4;

   public void loadFromFooObject(Foo fooObj)
   {
      this.var1 = fooObj.var1;
      this.var2 = fooObj.var2;
   }
}

So that I can avoid doing:

Foo[] fooObjs = { new Foo(), new Foo(), new Foo()};
Bar[] barObjs = new Bar[fooObjs.Length];
for (int i = 0; i < fooObjs.Length; i++)
{
   barObjs[i].loadFromFooObject(fooObjs[i]);
}

And do something like:

Foo[] fooObjs = { new Foo(), new Foo(), new Foo()};
Bar[] barObjs = fooObjs.Parse(loadFromFooObject);

Is something like this possible using C# and/or Linq?

1
  • Your code could be pseudo-code but barObjs[i].loadFromFooObject would raise a NRE. You can probably have a static method in your class Bar and call that to transform. Commented Feb 27, 2015 at 14:13

4 Answers 4

3

Write a method TransformFooToBar and then use the linq, e.g.,

var barObjs = fooObjs.Select(n => TransformFooToBar(n)).ToArray(); 

If you really want it to be a method on the Bar class, write an extension method, and then linq looks like this:

var barObjs = fooObjs.Select(n => n.TransformFooToBar()).ToArray(); 
Sign up to request clarification or add additional context in comments.

3 Comments

You could even go one step further and write an overloaded extension method to extend the IEnumerable<Foo> itself to call the above LINQ select statement. It would look like var barObjs = fooObjs.TransformFoosToBars();
It should be mentioned that if it's left as a static method, the first version can be written slightly more simply as: fooObjs.Select( TransformFooToBar ).ToArray(). Naturally if it's an extension method this will also work (provided the static class name is included).
@ryanyuyu This seems to be interesting. Could you show that approach in an answer maybe? :)
1

I use this strategy a lot for any kind of object conversion/mapping:

  • Create the function for a single object conversion
  • Create an overload accepting an IEnumerable (usually a List for me) and use LINQ .Select to convert the entire list into. It codes seamlessly since the single object conversion is, by definition, a Func. See this SO answer for more explanation on Funcs.

You can also get fancy with extension methods by creating a few extension methods in a static class. For you case specifically, the extension methods could look like this:

public static class ExtensionMethods
{
    public static Bar ToBar(this Foo foo)
    {
        var bar = new Bar();
        bar.loadFromFooObject(foo);
        //you could also move the logic to convert from the Bar class in here
        return bar;
    }

    //Overload for a collection of Foos (like Foo[] or List<Foo>)
    public static IEnumerable<Bar> ToBars(this IEnumerable<Foo> foos)
    {
        //Since ToBar is a Func<Foo, Bar>
        return foos.Select(ToBar);
        //alternate lambda syntax:  return foos.Select(foo => foo.ToBar());
    }
}

And you would call these methods like this:

var fooList = new List<Foo>();
var barEnumerable = fooList.ToBars();

1 Comment

This in my opinion is a neat way to do it. Looks super clean in the code! Thank you a lot :)
1

This something like this, all you need to create a ConvertToBar method which takes a Foo and returns a Bar.

var barObjs = fooObjs.Select(i=>ConvertToBar(i)).ToArray();

2 Comments

Create the ConvertToBar Method in which context?
I don't think it belongs to either object. Create it in a factory class.
0

My preference (and it is just a personal preference) is to override the explicit cast operator and just cast from one type to the other. Combine that with Kye's answer to handle multiple objects.

Comments

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.