2017-06-07 4 views
1

J'ai utilisé un paquet nuget appelé ICal.net pour charger les fichiers ics afin de vérifier les événements qui ont été récemment ajoutés.Comparaison du calendrier ICal.net

J'ai remarqué lors de l'utilisation de la méthode IEnumerable Except pour cela que certains événements sont manqués même si vous pouvez voir que plus d'événements ont été ajoutés.

je suis tombé sur la Uid propriété en cas, vérifié dehors et a remarqué que son unique - https://github.com/rianjs/ical.net/blob/5176d27ac243eb98a01157f2ed7ff3e2852b98eb/v2/ical.NET/Interfaces/Components/IUniqueComponent.cs#L14

J'ai écrit un IEqualityComparer<IEvent> pour cela en utilisant l'uid mais maintenant tous les événements sont considérés comme des nouveaux événements. Je me demandais juste si quelqu'un avait des suggestions sur la façon dont je peux prendre 2 calendriers, comparer les événements et obtenir les différences? Actuellement, il y a plus de 2000 événements et de plus en plus d'essayer de le garder performant.

+1

Découvrez blog Marius Schulz au sujet des mises en garde considèrent l'exception (https://blog.mariusschulz.com/2011/08/08/why-enumerableexcept-might -not-work-the-way-you-could-expect) – robjam

Répondre

0

Si je vous comprends bien, vous avez deux collections de calendriers. L'un représente un VCALENDAR avec plusieurs VEVENT et le second représente le même VCALENDAR + VEVENT à un moment ultérieur. Souvent, le VCALENDAR plus tard a plus d'événements que le calendrier précédent, pour des raisons évidentes. Et vous voulez comparer les deux pour voir la différence, c'est-à-dire trouver les nouveaux événements.

  • L'utilisation de Uid peut être suffisante et peut ne pas l'être; Cela dépend de votre système d'agenda. Bien que chaque UID soit unique, c'est à votre application de garantir. Quand ical.net crée un événement, il fait Guid.NewGuid().ToString(), donc si vous utilisez ical.net pour créer des événements, ils doivent être uniques. Google Calendar et (je suppose) d'autres applications de calendrier populaires fournissent également des Uids déterministes.
  • ical.net ne considère pas le Uid significatif à des fins d'égalité ou de hachage. Au lieu de cela, il prête attention à la composition des événements eux-mêmes.

Si vous savez que UID est unique, et vous avez aucun intérêt à comparer deux événements avec UIDS inégalés de chaque événement, je ferais quelque chose comme ceci:

var eventIdSet = new HashSet<string>(StringComparison.OrdinalIgnoreCase); 
var firstEventIds = firstCalendarCollection 
    .SelectMany(cc => cc.Event) 
    .Select(e => e.Uid); 
eventIdSet.UnionWith(firstEventIds); 

var secondEventIds = secondCalendarCollection 
    .SelectMany(cc => cc.Event) 
    .Select(e => e.Uid); 

eventIdSet.ExceptWith(secondEventIds); 

Cela devrait vous donner le nouveau calendrier ids présents dans la première collection, mais pas la seconde.

Si vous voulez comparer le contenu de l'événement, je ferais le même schéma, arrêt à l'objet Event:

var firstSet = new HashSet<Event>(); 
var firstEvents = firstCalendarCollection.SelectMany(cc => cc.Event); 
firstSet.UnionWith(firstEventIds); 

var secondEvents = secondCalendarCollection.SelectMany(cc => cc.Event); 
firstSet.ExceptWith(secondEvents); 

Cela va faire la même chose, mais comme je l'ai dit plus haut, ids d'événement sont ignorés par les implémentations internes GetHashCode et Equals. Comparer Uid s seul sera plus rapide que de comparer le contenu entier de chaque Event. Cela dit, à moins que ce soit une application serveur occupée qui doit le faire plusieurs fois par seconde, cela ne devrait pas avoir d'importance. Nous utilisons ical.net, et effectuons des opérations comme celle-ci avec 800-1000 événements de calendrier, et des millisecondes de temps de calcul dans une application WPF.Vous ne remarquerez probablement pas la différence entre les comparaisons Uid et toute la comparaison de contenu Event sauf dans des circonstances extrêmes.

Edit: J'ai créé une page wiki: https://github.com/rianjs/ical.net/wiki/Comparing-collections-of-calendar-events

+0

Je suis confronté à un problème avec ical.net. Créer un calendrier dans mon application .Net en utilisant ical.net. Cependant, dans mon environnement, les e-mails du calendrier semblent bien, avec la possibilité d'accepter ou de rejeter. Dans l'environnement des clients, il n'y a pas d'option pour accepter ou annuler cette demande. Cela se passe uniquement avec le client sur Outlook 2010 et Outlook 2016 aussi. Cependant, dans notre environnement, nous voyons les e-mails du calendrier très bien sur les perspectives 2010 et 2016. Toute aide sera appréciée! Merci – k2ibegin

0

Je recommanderais de faire une requête Where In avec LINQ.

en supposant que vous avez deux collections (enregistrés et éventuellement nouvelles):

List<string> registeredIds = GetRegisteredComponentsUIds(); 

List<ComponentImplemenation> newEvents = GetNewEvents(); 

List<ComponentImplemenation> result = newEvents.Where(m => registeredIds.Contains(m.Uid)) 
               .ToList();