/// <summary> /// Compares two collections of objects of type <typeparamref name="T"/>. /// </summary> /// <param name="list1">The first collection</param> /// <param name="list2">The second collection</param> /// <returns>A list of <see cref="ObjectComparison{T}"/> records representing the results of the comparison of the two collections</returns> public IReadOnlyCollection <ObjectComparison <T> > Compare(IReadOnlyCollection <T> list1, IReadOnlyCollection <T> list2) { IDictionary <string, T> dict1, dict2; try { dict1 = list1.ToDictionary(_ => this.keyProvider.GetKey(_)); } catch (ArgumentException) { throw new ComparisonException($"Comparer <{this.Name}> by key <{this.keyProvider.Name}>: List1 contains duplicate values by key!"); } try { dict2 = list2.ToDictionary(_ => this.keyProvider.GetKey(_)); } catch (ArgumentException) { throw new ComparisonException($"Comparer <{this.Name}> by key <{this.keyProvider.Name}>: List2 contains duplicate values by key!"); } var resultList = new List <ObjectComparison <T> >(); foreach (var kvp in dict1) { var item1 = kvp.Value; ObjectComparison <T> comparison; if (!dict2.TryGetValue(kvp.Key, out T item2)) { this.equalityComparer.Equals(item1, null, out List <Difference> differentProperties); comparison = ObjectComparison <T> .OnlyItem1(kvp.Key, item1, differentProperties); } else { comparison = DeepCompare(kvp.Key, item1, item2); } resultList.Add(comparison); } foreach (var kvp in dict2) { var item2 = kvp.Value; if (dict1.ContainsKey(kvp.Key)) { continue; } this.equalityComparer.Equals(null, item2, out List <Difference> differentProperties); var comparison = ObjectComparison <T> .OnlyItem2(kvp.Key, item2, differentProperties); resultList.Add(comparison); } return(resultList); }
/// <summary> /// Uses the equality comparer to compare two objects of the collection in order to identify whether they are equal or /// different by some property. /// </summary> /// <param name="key">The objects key</param> /// <param name="item1">The first item</param> /// <param name="item2">The second item</param> /// <returns>An instance of <see cref="ObjectComparison{T}"/> that represents the result of the comparison</returns> private ObjectComparison <T> DeepCompare(string key, T item1, T item2) { var areEqual = this.equalityComparer.Equals(item1, item2, out List <Difference> differentProperties); if (areEqual) { return(ObjectComparison <T> .Equals(key, item1, item2)); } return(ObjectComparison <T> .MatchingButDifferent(key, item1, item2, differentProperties)); }