Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is there a jQuery extend in c#?

 var _Contact = new ContactLstModel { 
             ContactName="xxxxxx",
              EmailAddr="yyyyyy",
               ContactNo="ddddddd",
               SelectedContactType="dddd"
            };

 var _ContactOption= new ContactLstModel{
                 ContactType= new List<SelectListItem>(){
                 new SelectListItem{
                  Text="sss",Value="ddd"
                 }
                 }
            };

as you can see both are of the same model ContactLstModel. Now how do I combine both into one?

Like in jQuery, we have $.extend(dest,source);

Is there an equivalent in C#?

like image 293
Irshu Avatar asked Oct 02 '14 08:10

Irshu


2 Answers

There is not a built-in equivalent of $.extend in C# and .NET 4.5.

However you can find many examples of people trying to achieve that kind of behavior using reflection in .NET. There are others who use serialization (JSON.NET etc.) to achieve similar behaviors . Another approach would be to use IOC containers like Automapper.

Here is an example how to merge your first object into the second object using Automapper IOC:

var expr = Mapper.CreateMap<ContactLstModel, ContactLstModel>().ForMember("ContactType", (conf) => { conf.Ignore(); });
var merged = Mapper.Map<ContactLstModel, ContactLstModel>(_Contact, _ContactOption);

With Automapper you can control how to map each single property from source to destination.

If you don't want external library dependencies, and want full control you can use a pure Reflection approach.

For example you could use something similar as the CopyValues method from this link and merge the second object properties with the first one using reflection.

CopyValues<ContactLstModel>(_Contact, _ContactOption);

So this line of code will copy the ContactType property values from the second object into the first one.

CopyValues uses reflection to loop through the properties of the objects:

public static void CopyValues<T>(T target, T source)
{
    Type t = typeof(T);

    var properties = t.GetProperties().Where(prop => prop.CanRead && prop.CanWrite);

    foreach (var prop in properties)
    {
        var value = prop.GetValue(source, null);
        if (value != null)
            prop.SetValue(target, value, null);
    }
}

Of course this does not support everything jquery extend does (merging, shallow and deep cloning into a new object etc.), but it can satisfy your current needs. You can extend on these principles and build a more comprehensive solution.

However have in mind that C# is not a language like Javascript, and the cost of doing reflection is much higher in C#, while in Javascript the properties of a prototype can be listed with a cheap for-in iteration, or with a call to Object.keys().

like image 123
Faris Zacina Avatar answered Oct 04 '22 12:10

Faris Zacina


You could do it with an extension method:

public static class ContactModelExtensions {
    public static ContactModel Extend(this ContactModel first, ContactModel replacement) {
        if (!replacement.ContactsName.IsNullOrEmpty()) // or whatever criteria you want
        {
            first.ContactsName = replacement.ContactsName;
        }
        // similar assignment for all other properties

        return first; // since we return the first one, properties not set in override
                      // will be untouched
    }
}

Now, you can just

var extendedContact = _Contact.Extend(_ContactOptions);

to get it done.

like image 44
Tomas Aschan Avatar answered Oct 04 '22 13:10

Tomas Aschan