using System;
using System.Collections.Generic;
using System.Linq;
using System.Reactive.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Adaptation
{
    static class Examples36_38
    {
        // Listing 11-36
        public static void ShowAll(IEnumerable<string> source)
        {
            IObservable<string> observableSource = source.ToObservable();
            observableSource.Subscribe(Console.WriteLine);
        }

        public static void UseToObservable()
        {
            ShowAll(Enumerable.Range(1, 10).Select(i => i.ToString()));
        }

        // Listing 11-37
        public static IObservable<T> MyToObservable<T>(this IEnumerable<T> input)
        {
            return Observable.Create((IObserver<T> observer) =>
            {
                bool inOnNext = false;
                try
                {
                    foreach (T item in input)
                    {
                        inOnNext = true;
                        observer.OnNext(item);
                        inOnNext = false;
                    }
                    observer.OnCompleted();
                }
                catch (Exception x)
                {
                    if (inOnNext)
                    {
                        throw;
                    }
                    observer.OnError(x);
                }
                return () => { };
            });
        }

        public static void UseMyToObservable()
        {
            IEnumerable<string> source = Enumerable.Range(1, 10).Select(i => i.ToString());
            IObservable<string> observableSource = source.MyToObservable();
            observableSource.Subscribe(Console.WriteLine);
        }

        // Listing 11-38
        public static void ShowAll(IObservable<string> source)
        {
            foreach (string s in source.ToEnumerable())
            {
                Console.WriteLine(s);
            }
        }

        public static void UseToEnumerable()
        {
            ShowAll(Observable.Generate(1, x => x <= 10, x => x + 1, x => x.ToString()));
        }
    }
}
