Esempio n. 1
0
        public static IReactiveDictionary <TKey, TValue> Where <TKey, TValue>(this IReactiveDictionary <TKey, TValue> dict, Func <TKey, TValue, bool> selector)
        {
            return(dict
                   .AsObservable()
                   .Select(changes => changes
                           .Select(change => {
                if (change.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate && !selector(change.Key, change.Value))
                {
                    if (dict.TryGetValue(change.Key, out var value))
                    {
                        return new ReactiveDictionaryChange <TKey, TValue>(change.Key, value, ReactiveDictionaryChangeReason.Remove);
                    }
                    else
                    {
                        return null;
                    }
                }
                else
                {
                    return change;
                }
            })
                           .Where(x => x != null)
                           .ToArray()
                           )
                   .Where(x => x.Any())
                   .ToDictionary((TKey key, out TValue value) => {
                if (!dict.TryGetValue(key, out value))
                {
                    return false;
                }

                return selector(key, value);
            }));
        }
Esempio n. 2
0
        public static IReactiveSet <KeyValuePair <TKey, TValue> > ToSet <TKey, TValue>(this IReactiveDictionary <TKey, TValue> dict)
        {
            return(dict.AsObservable().SelectMany(changes => changes.SelectMany(change => {
                if (change.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate)
                {
                    if (dict.TryGetValue(change.Key, out var oldValue))
                    {
                        // Updating, so remove the old pair and add the new one
                        return new[] {
                            new ReactiveSetChange <KeyValuePair <TKey, TValue> >(
                                ReactiveSetChangeReason.Remove,
                                new[] { new KeyValuePair <TKey, TValue>(change.Key, oldValue) }
                                ),
                            new ReactiveSetChange <KeyValuePair <TKey, TValue> >(
                                ReactiveSetChangeReason.Add,
                                new[] { new KeyValuePair <TKey, TValue>(change.Key, change.Value) }
                                )
                        };
                    }
                }

                // Just adding or removing
                return new[] {
                    new ReactiveSetChange <KeyValuePair <TKey, TValue> >(
                        change.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate ? ReactiveSetChangeReason.Add : ReactiveSetChangeReason.Remove,
                        new[] { new KeyValuePair <TKey, TValue>(change.Key, change.Value) }
                        )
                };
            }))
                   .ToReactiveSet(pair => dict.TryGetValue(pair.Key, out var value) && value.Equals(pair.Value)));
        }
Esempio n. 3
0
        public static IReactiveDictionary <TKey, TNewValue> SelectEquatable <TKey, TValue, TNewValue>(
            this IReactiveDictionary <TKey, TValue> dict,
            Func <TKey, TValue, TNewValue> selector) where TNewValue : IEquatable <TNewValue>
        {
            return(dict.AsObservable().Select(changes => changes.Select(change => {
                if (change.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate)
                {
                    return new ReactiveDictionaryChange <TKey, TNewValue>(change.Key, selector(change.Key, change.Value), ReactiveDictionaryChangeReason.AddOrUpdate);
                }
                else if (dict.TryGetValue(change.Key, out var value))
                {
                    return new ReactiveDictionaryChange <TKey, TNewValue>(change.Key, selector(change.Key, change.Value), ReactiveDictionaryChangeReason.Remove);
                }
                else
                {
                    return null;
                }
            }))
                   .ToDictionary((TKey key, out TNewValue value) => {
                if (dict.TryGetValue(key, out var oldValue))
                {
                    value = selector(key, oldValue);
                    return true;
                }

                value = default;
                return false;
            }));
        }
Esempio n. 4
0
 public static IObservable <TKey> ElementsRemoved <TKey, TValue>(this IReactiveDictionary <TKey, TValue> dict)
 {
     return(dict
            .AsObservable()
            .Select(x => x.Where(y => y.ChangeReason == ReactiveDictionaryChangeReason.Remove))
            .SelectMany(x => x)
            .Select(x => x.Key));
 }
Esempio n. 5
0
 public static IObservable <KeyValuePair <TKey, TValue> > ElementsAddedOrUpdated <TKey, TValue>(this IReactiveDictionary <TKey, TValue> dict)
 {
     return(dict
            .AsObservable()
            .Select(x => x.Where(y => y.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate))
            .SelectMany(x => x)
            .Select(x => new KeyValuePair <TKey, TValue>(x.Key, x.Value)));
 }
Esempio n. 6
0
        public static IObservable <TResult> Aggregate <TKey, TValue, TResult>(
            this IReactiveDictionary <TKey, TValue> dict,
            TResult seed,
            Func <TResult, TKey, TValue, TResult> addFunc,
            Func <TResult, TKey, TValue, TResult> removeFunc)
        {
            if (dict == null)
            {
                throw new ArgumentNullException(nameof(dict));
            }
            if (addFunc == null)
            {
                throw new ArgumentNullException(nameof(addFunc));
            }
            if (removeFunc == null)
            {
                throw new ArgumentNullException(nameof(removeFunc));
            }

            return(Observable.Create <TResult>(observer => {
                var current = seed;
                observer.OnNext(current);

                IDisposable sub = null;
                sub = dict
                      .AsObservable()
                      .Subscribe(
                    x => {
                    foreach (var change in x)
                    {
                        try {
                            if (change.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate)
                            {
                                current = addFunc(current, change.Key, change.Value);
                            }
                            else
                            {
                                current = removeFunc(current, change.Key, change.Value);
                            }
                        }
                        catch (Exception ex) {
                            observer.OnError(ex);
                            sub?.Dispose();
                            return;
                        }
                    }

                    observer.OnNext(current);
                },
                    observer.OnError,
                    observer.OnCompleted
                    );

                return sub;
            })
                   .DistinctUntilChanged());
        }
Esempio n. 7
0
 public static IObservable <TValue> LatestValue <TKey, TValue>(this IReactiveDictionary <TKey, TValue> dict, TKey key)
 {
     return(dict
            .AsObservable()
            .SelectMany(changes => changes
                        .Where(x => x.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate)
                        .Where(x => x.Key.Equals(key)))
            .Select(x => x.Value));
 }
Esempio n. 8
0
        public static IReactiveDictionary <TKey, TValue> SubscribeMany <TKey, TValue>(this IReactiveDictionary <TKey, TValue> dict, Func <TKey, TValue, IDisposable> subscriptionFactory)
        {
            var seq = Observable.Create <IEnumerable <ReactiveDictionaryChange <TKey, TValue> > >(observer => {
                Dictionary <KeyValuePair <TKey, TValue>, IDisposable> subs = new Dictionary <KeyValuePair <TKey, TValue>, IDisposable>();

                var disposable1 = dict.AsObservable().Subscribe(
                    changes => {
                    foreach (var change in changes)
                    {
                        if (dict.ContainsKey(change.Key))
                        {
                            if (subs.TryGetValue(change.Pair, out var sub))
                            {
                                sub.Dispose();
                            }
                        }

                        if (change.ChangeReason == ReactiveDictionaryChangeReason.AddOrUpdate)
                        {
                            subs[change.Pair] = subscriptionFactory(change.Key, change.Value);
                        }
                    }

                    observer.OnNext(changes);
                },
                    observer.OnError,
                    observer.OnCompleted
                    );

                return(() => {
                    disposable1.Dispose();

                    foreach (var sub in subs)
                    {
                        sub.Value.Dispose();
                    }
                });
            });

            return(seq.ToDictionary(dict.TryGetValue));
        }
Esempio n. 9
0
        public static IReactiveDictionary <TKey, TValue> Join <TKey, TValue>(this IReactiveDictionary <TKey, TValue> dict, IReactiveDictionary <TKey, TValue> dict2)
        {
            var obs1 = dict.AsObservable().Select(changes => changes.Select(change => {
                if (change.ChangeReason == ReactiveDictionaryChangeReason.Remove)
                {
                    if (dict2.TryGetValue(change.Key, out var value))
                    {
                        return(new ReactiveDictionaryChange <TKey, TValue>(change.Key, value, ReactiveDictionaryChangeReason.AddOrUpdate));
                    }
                }

                return(change);
            }));

            var obs2 = dict2.AsObservable().Select(changes => changes.Select(change => {
                if (change.ChangeReason == ReactiveDictionaryChangeReason.Remove)
                {
                    if (dict2.TryGetValue(change.Key, out var value))
                    {
                        return(new ReactiveDictionaryChange <TKey, TValue>(change.Key, value, ReactiveDictionaryChangeReason.AddOrUpdate));
                    }
                }

                return(change);
            }));

            return(obs1.Merge(obs2)
                   .Select(x => x.ToArray())
                   .Where(x => x.Length > 0)
                   .ToDictionary((TKey key, out TValue value) => {
                if (dict.TryGetValue(key, out value))
                {
                    return true;
                }

                return dict2.TryGetValue(key, out value);
            }));
        }
 public static ICollectedReactiveDictionary <TKey, TValue> ToConcurrentDictionary <TKey, TValue>(
     this IReactiveDictionary <TKey, TValue> dict)
 {
     return(new DependentReactiveDictionary <TKey, TValue>(dict.AsObservable(), new ConcurrentDictionary <TKey, TValue>()));
 }
 public static ICollectedReactiveDictionary <TKey, TValue> ToDictionary <TKey, TValue>(
     this IReactiveDictionary <TKey, TValue> dict,
     IDictionary <TKey, TValue> inner)
 {
     return(new DependentReactiveDictionary <TKey, TValue>(dict.AsObservable(), inner));
 }