samedi 4 avril 2020

Need design decision for updating ObservableCollection in the cloned copy

As part of my application, I am maintaining a cache which is structured like below,

class Container
{

       List<ExecEnv> ExecEnvList;
       List<ControlMod> ToBeProcessedControlModList;
       // Other Properties goes here
       // Other properties can be either simple type or List of other objects etc..,
     .....
}

class ExecEnv
{
       ObservableCollection<ContMod> ExistingContModList;
       ObservableCollection<ContMod> NewContModList;

       // Other Properties goes here
       // Other properties can be either simple type or List of other objects etc.., 

}

class ContMod
{ 
      // Lot of properties, It will be either simple type, list or dictionary

}

The Cache is dictionary of Container,

       Dictionary<int,Container>  IDToContainerList;

Initially, NewContModList is empty inside Container. The business logic will process each Container and distribute ToBeProcessedControlModList to all the ExecEnvto it. I don't want to update this NewContModList in the Cache. This NewContModList should be updated to ExecEnv whenever the client requests it.

So I am maintaining one more map, which has ExectionEnv id as key and list of newControlMod id as the value

    Dictionary<int,List<int>> ExecEnvIDToNewContModList; 

The client request for the data in the following method,

     GetNewAssignments(int ContainerId, ref List<ExecEnv> processedList)
     {

           // Check the avaialability of Cotnaier in dictionary here;
           if(IDToContainerList.ContainsKey(ContainerId))
           {

                Container cont = IDToContainerList[ContainerId];

                // Get ExecEnv List copy from the requested Container and update new List

                processedList = cont.ExecEnvList.Clone();   // Assume clone extension method is implemented for List

                // Logic to Update NewContMod List here
           }                     

     }

     The above code updates NewContMod in my cache as well. I don't want this behavior.

I wanted the NewContMod list should be updated only on the processed list ref argument.

So implemented Clone method in ExecEnv as below,

    public object Clone()
    {
        var obj = (ExecEnv) this.MemberwiseClone();

        obj.ExistingContModList = new ObservableCollection<ContMod>(ExistingContModList.Select(x => (ControlMod)x.Clone()).ToList());
        obj.NewContModList = new ObservableCollection<ContMod>(NewContModList.Select(x => (ControlMod)x.Clone()).ToList());


        return obj;
    }

After doing this achieved whatever I want. The NewContModList is updated only on the processList ref argument. NewContModList is not updated in original cache.

I am coming from C++ background, My understanding is all C# objects are reference type so we need clone method to get clone copy. So in the above approach I need to clone of other list objects as like above.

So I need experts help to understand is there any better design approach to handle this above scenario?

Aucun commentaire:

Enregistrer un commentaire