J'ai une liste qui contient des données et parfois elle contient des lignes en double et je veux supprimer cette ligne en double pour celle que j'ai utilisée ci-dessous le code
num = numDetailsTemp.Distinct().ToList(); var query = num.GroupBy(o => new { o.Number }) .Select(group => new { Name = group.Key, Numbers = group.OrderByDescending(x => x.Date) }) .OrderBy(group => group.Numbers.First().Date); List<NumberDetails> numTemp = new List<NumberDetails>(); foreach (var group in query) { foreach (var numb in group.Numbers) { numTemp.Add(numb); break; } } num = numTemp;
L'image ci-dessous montre la valeur en double du list.
Et quand j'applique supprimer les doublons, cela me donne une sortie
Mais je veux supprimer cette ligne qui ne contient pas d'alter no ou de preuve d'identité et de date comme indiqué dans la première image, première ligne non, contient AlterNo et ID preuve et date et la deuxième ligne contient cela, donc je veux supprimer la première ligne et n'afficher que la deuxième ligne. La date est obligatoire pour vérifier et après cela AlterNo et preuve d'identité.
3 Réponses :
Vous pouvez éliminer les doublons en utilisant l'opérateur Distinct
. Vous devez d'abord définir une classe de comparateur qui implémente l'interface IEqualityComparer
, puis la transmettre à l'opérateur distinct de votre méthode.
var distinctRecords = source.Distinct(new NumberDetailsComparer());
Et voici comment l'utiliser :
internal class NumberDetailsComparer : IEqualityComparer<NumberDetails> { public bool Equals(NumberDetails x, NumberDetails y) { if (\* Set of conditions for equality matching *\) { return true; } return false; } public int GetHashCode(Student obj) { return obj.Name.GetHashCode(); // Name or whatever unique property } }
Tout ce que vous avez à faire est de définir les critères de la classe de comparaison. J'espère que cela résout votre problème.
Ce lien pourrait être utile pour un exemple pleinement fonctionnel:
Ma liste contient uniquement des données distinctes
distinct est un terme relatif, vous dans la classe de comparaison devez lui dire ce qui est distinct. dans votre cas, les enregistrements qui n'ont pas de valeur pour les champs mentionnés ne doivent pas être choisis.
Vous pouvez essayer ce qui suit:
var group = list .GroupBy(r => r.Number) .SelectMany(g => g) //flatten your grouping and filter where you have alterno and id .Where(r => !string.IsNullOrEmpty(r.AlterNo) && !string.IsNullOrEmpty(r.Id)) .OrderByDescending(r=>r.Date) .ToList();
Je veux une date aussi parce que le principal est la date, puis l'alteno et la preuve d'identité
Votre question ne précise pas cela ainsi que l'image que vous avez publiée. Mettez à jour votre question pour la rendre plus claire.
Votre image montre que les deux lignes ont des dates. Que voulez-vous exactement? Les 3 champs doivent-ils être présents pour être choisis?
Oui, je compare la date car je veux une date récente et non la date précédente.Si les enregistrements en double ont la même date, comparez la preuve d'identité et AlterNo et supprimez ceux qui ne contiennent pas de preuve d'identité et Alterno
Vous avez donc une séquence de NumberDetails
, et une définition du moment où vous considérez que NumberDetails
est égal.
Une fois que vous avez trouvé quel NumberDetails sont égaux, vous souhaitez éliminer les doublons, sauf un: un duplicata qui a des valeurs pour
AlterNo
et IdProof
.
Hélas vous ne l'avez pas fait ne spécifiez pas ce que vous voulez s'il n'y a pas de doublons avec des valeurs pour AlterNo
et IdProof
. Ni ce que vous voulez s'il y a plusieurs doublons avec des valeurs pour AlterNo
et IdProof
.
Mais supposons que s'il y a plusieurs de ces éléments, vous s'en fout: choisissez-en un, car ce sont des doublons de toute façon.
Dans votre exigence, vous parlez de doublons. Alors écrivons une classe qui implémente vos exigences d'égalité:
var groupsEqualNumberDetails = numberDetails.GroupBy( // keySelector: make groups with equal NumberDetails: numberDetail => numberDetail, // ResultSelector: take the key and all NumberDetails thas equal this key: // and keep the first one that has values for AlterNo and IdProof (key, numberDetailsEqualToKey) => numberDetailsEqualToKey .Where(numberDetail => numberDetail.AlterNo != null && numberDetail.IdProof != null) .FirstOrDefault(), // KeyComparer: when do you consider two NumberDetails equal? NumberDetailEqualityComparer.Default; }
Vous devez également implémenter GetHashCode. Vous pouvez retourner tout ce que vous voulez, tant que vous sont certains que si x et y sont égaux, ils renvoient le même HashCode De plus, il serait plus efficace que si x et y ne sont pas égaux, alors il y a une forte probabilité pour un HashCode différent.
Quelque chose comme:
public int GetHashCode(NumberDetail numberDetail) { const int prime1 = 12654365; const int prime2 = 54655549; if (numberDetail == null) return prime1; int hash = prime1; unsafe { hash = prime2 * hash + numberDetail.Number.GetHashCode(); hash = prime2 * hash + numberDetail.FullName.GetHashCode(); hash = prime2 * hash + numberDetail.Date.GetHashCode(); ... } return hash;
Bien sûr, vous devez vérifier si l'une des propriétés est égale à NULL avant de demander le HashCode.
Évidemment dans votre égalité (et donc dans GetHashCode) vous ne regardez ni AlterNo
ni IdProof
.
Une fois que vous avez défini précisément lorsque vous considérez deux NumberDetails
égaux, vous pouvez créer des groupes de NumberDetails
class NumberDetailEqualityComparer : IEqualityComparer<NumberDetail> { public static IEQualityComparer<NumberDetail> Default {get;} = new NumberDetaulEqualityComparer(); public bool Equals(NumberDetail x, NumberDetail y) { if (x == null) return y == null; // true if both null if (y == null) return false; // because x not null and y null if (Object.ReferenceEquals(x, y) return true; // because same object if (x.GetType() != y.GetType()) return false; // because not same type // by now we are out of quick checks, we need a value check return x.Number == y.Number && x.FullName == y.FullName && ... // etc, such that this returns true if according your definition // x and y are equal }
p>