Search code examples
c#design-patternsrefactoringtemplate-method-pattern

C# Refactoring the same action with different details using design patterns


I try to find the way for refactoring my code but no idea how to do this.

For example, we have several classes

class A {
     string name;
     int year;
}

class B {
      long id;
      string code; 
      DateTime currentTime;
}

class C {
      string lastname;
      DateTime currentDate; 
}

And latter I need to return list of objects of these classes List, List, List and convert them into Object[][].

For every conversion I do the same

private Object[][] converAListToObjectArray(List<A> dataList)
        {
            long countRecords = dataList.Count();
            const int countProperty = 2;
            var arrayRes = new object[countRecords][];

            for (int i = 0; i < countRecords; i++)
            {
                var arrayObjProperty = new object[countProperty];
                arrayObjProperty[0] = dataList[i].Name;
                arrayObjProperty[1] = dataList[i].Year;

                arrayRes[i] = arrayObjProperty;
            }
            return arrayRes;
        }

private Object[][] converBListToObjectArray(List<B> dataList)
        {
            long countRecords = dataList.Count();
            const int countProperty = 3;
            var arrayRes = new object[countRecords][];

            for (int i = 0; i < countRecords; i++)
            {
                var arrayObjProperty = new object[countProperty];
                arrayObjProperty[0] = dataList[i].Id;
                arrayObjProperty[1] = dataList[i].Code;
                arrayObjProperty[2] = dataList[i].CurrentTime; 

                arrayRes[i] = arrayObjProperty;
            }
            return arrayRes;
        }

Is it possible separate this convertion using some design pattern?


Solution

  • You could use an action and do something like this: -

    class Program
    {
        // Your new function, (doesn't have to be static; just did it for the demo)
        // If you really really want to return object[][] still,
        // You'll need to pass an index to foo as well
        private static List<IList<object>> convert<T>(IList<T> dataList, Action<IList<object>, T> foo)
        {
            var arrayRes = new List<IList<object>>();
    
            foreach (var item in dataList)
            {
                var arrayObjProperty = new List<object>();
                foo(arrayObjProperty, item);
    
                arrayRes.Add(arrayObjProperty);
            }
            return arrayRes;
        }
    
        // The rest is just calling the function with two examples
        static void Main(string[] args)
        {
            var bar = new List<A>();
            bar.Add(new A() { name = "qux", year = 2013 });
    
            var objects1 = convert(bar, (a, b) =>
            {
                a.Add(b.name);
                a.Add(b.year);
            });
    
            var baz = new List<B>();
            baz.Add(new B() { code = "qux", id = 2013 });
    
            var objects2 = convert(baz, (a, b) =>
            {
                a.Add(b.code);
                a.Add(b.id);
            });
        }
    }
    

    You can just copy this into your IDE to have a play and see how it works. Basically, this uses generics and then an action to allow you to do the only part that differs each time in a lambda that is passed to the method.