// ========================================================================
//
// Copyright (C) 2016-2017 MARC CHEVALDONNE
//                         marc.chevaldonne.free.fr
//
// Module        : Program.cs
// Author        : Marc Chevaldonné
// Creation date : 2016-10-03
//
// ========================================================================

using System;
using System.Collections.Generic;
using System.Linq;
using static System.Console;

namespace ex_031_006_LINQ_filtering
{
    class Program
    {
        static void Main(string[] args)
        {
            List<Nounours> nounours = new List<Nounours> {
                                      new Nounours("mouton", new DateTime(2009, 09, 16)),
                                      new Nounours("ours", new DateTime(2009, 08, 15)),
                                      new Nounours("chat", new DateTime(2009, 07, 14)),
                                      new Nounours("chien", new DateTime(2009, 06, 13)),
                                      new Nounours("lapin", new DateTime(2009, 05, 12)),
                                      new Nounours("chat", new DateTime(2009, 07, 14)),
                                      new Nounours("macaque", new DateTime(2009, 04, 11))};

            /////////////
            //Filtering//
            /////////////
            WriteLine("Filtering");

            //Where : condition
            WriteLine("Where");
            IEnumerable<Nounours> filtered = nounours.Where(n => n.Nom.StartsWith("c"));
            foreach (Nounours n in filtered)
            {
                WriteLine($"{n} ");
            }
            WriteLine();

            //la même requête en query syntax
            WriteLine("Where");
            IEnumerable<Nounours> filteredQuerySyntax = from n in nounours
                                                        where n.Nom.StartsWith("c")
                                                        select n;
            foreach (Nounours n in filteredQuerySyntax)
            {
                WriteLine($"{n} ");
            }
            WriteLine();

            //Take : prend les n premiers
            WriteLine("Take");
            IEnumerable<Nounours> taken = nounours.Take(3);
            foreach (Nounours n in taken)
            {
                WriteLine($"{n} ");
            }
            WriteLine();

            //TakeWhile : prend les premiers tant qu'une condition est vérifiée
            WriteLine("TakeWhile");
            IEnumerable<Nounours> takenwhile = nounours.TakeWhile(n => n.Naissance.Month > 6);
            foreach (Nounours n in takenwhile)
            {
                WriteLine($"{n} ");
            }
            WriteLine();

            //Skip : évite les n premiers
            WriteLine("Skip");
            IEnumerable<Nounours> skipped = nounours.Skip(3);
            foreach (Nounours n in skipped)
            {
                WriteLine($"{n} ");
            }
            WriteLine();

            //SkipWhile : évite les premiers tant qu'une condition est vérifiée
            WriteLine("SkipWhile");
            IEnumerable<Nounours> skippedwhile = nounours.SkipWhile(n => n.Naissance.Month > 7);
            foreach (var n in skippedwhile)
            {
                WriteLine($"{n} ");
            }
            WriteLine();

            //Distinct : retire les doublons
            //ATTENTION ! utilise le protocole d'égalité ! sinon, compare les références
            WriteLine("Distinct");
            IEnumerable<Nounours> distinct = nounours.Distinct();
            foreach (var n in distinct)
            {
                WriteLine($"{n} ");
            }
            WriteLine();

            //Where : variante avec index
            WriteLine("Where, variante avec index");
            IEnumerable<Nounours> filteredIndexedWhere = nounours.Where((n, i) => i % 2 == 0);
            foreach (Nounours n in filteredIndexedWhere)
            {
                WriteLine($"{n} ");
            }
            WriteLine();
        }
    }
}
