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

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

namespace ex_023_015_DictionaryCustomType
{
    class Program
    {
        /// <summary>
        /// exemple d'utilisation d'un dictionnaire sur un type personnalisé (une classe Nounours)
        /// 1. dans le premier cas, la classe (VieuxNounours) n'implémente pas le protocole d'égalité.
        /// L'exemple montre les problèmes qui peuvent apparaître : deux instances a priori égales ne sont pas comprises par le dictionnaire comme étant la même
        /// 2. dans le deuxième cas, la classe (Nounours) implémente le protocole d'égalité.
        /// Plus de problème.
        /// </summary>
        /// <param name="args"></param>
        static void Main(string[] args)
        {
            WriteLine("*****************************");
            WriteLine("TEST SANS PROTOCOLE D'EGALITE");
            WriteLine("*****************************");
            TestAvecVieuxNounours();

            WriteLine("\n\n\n");
            WriteLine("*****************************");
            WriteLine("TEST AVEC PROTOCOLE D'EGALITE");
            WriteLine("*****************************");
            TestAvecNounours();
        }

        static void TestAvecVieuxNounours()
        {
            VieuxNounours mouton = new VieuxNounours("mouton", new DateTime(2005, 04, 03), 2000);
            VieuxNounours ours = new VieuxNounours("ours", new DateTime(2006, 05, 04), 3000);
            VieuxNounours chien = new VieuxNounours("chien", new DateTime(2007, 06, 05), 1500);
            VieuxNounours girafe = new VieuxNounours("girafe", new DateTime(2008, 07, 06), 500);
            VieuxNounours dromadaire = new VieuxNounours("dromadaire", new DateTime(2012, 3, 11), 500);

            //préparation du dictionnaire
            var dico = new Dictionary<VieuxNounours, int>()
            {
                [mouton] = 0,
                [ours] = 0,
                [chien] = 0,
                [girafe] = 0,
                [dromadaire] = 0,
            };
            //on peut aussi utiliser cet equality comparer pour éviter le problème suivant
            //var dico = new Dictionary<VieuxNounours, int>(new VieuxNounoursNbPoilsEqualityComparer());

            //affichage du dictionnaire
            DisplayVieuxDico(dico);

            //on incrémente la valeur associée à la clé mouton, et celle associée à la clé chien
            dico[mouton]++;
            dico[chien]++;
            DisplayVieuxDico(dico);

            //on crée un nouveau chien (qui a les mêmes données que le premier, mais la référence n'est pas la même)
            VieuxNounours chien2 = new VieuxNounours("chien", new DateTime(2007, 06, 05), 1500);

            //chien2 n'est pas trouvé dans le dictionnaire car chien2 != chien, car ce sont des références différentes
            //(le protocole d'égalité n'a pas été réécrit)
            WriteLine(dico.ContainsKey(chien2));
            if (dico.ContainsKey(chien2))
            {
                dico[chien2]++;
            }
            else
            {
                dico.Add(chien2, 1);
            }
            DisplayVieuxDico(dico);
        }

        static void DisplayVieuxDico(Dictionary<VieuxNounours, int> dico)
        {
            WriteLine("**********************");
            foreach (KeyValuePair<VieuxNounours, int> pair in dico)
            {
                WriteLine($"{pair.Key.Name}   {pair.Value}");
            }
            WriteLine("**********************");
        }

        static void TestAvecNounours()
        {
            Nounours mouton = new Nounours("mouton", new DateTime(2005, 04, 03), 2000);
            Nounours ours = new Nounours("ours", new DateTime(2006, 05, 04), 3000);
            Nounours chien = new Nounours("chien", new DateTime(2007, 06, 05), 1500);
            Nounours girafe = new Nounours("girafe", new DateTime(2008, 07, 06), 500);
            Nounours dromadaire = new Nounours("dromadaire", new DateTime(2012, 3, 11), 500);

            //préparation du dictionnaire
            var dico = new Dictionary<Nounours, int>()
            {
                [mouton] = 0,
                [ours] = 0,
                [chien] = 0,
                [girafe] = 0,
                [dromadaire] = 0,
            };
            //var dico = new Dictionary<Nounours, int>(new NounoursNbPoilsEqualityComparer());

            //affichage du dictionnaire
            DisplayDico(dico);

            //on incrémente la valeur associée à la clé mouton, et celle associée à la clé chien dico[mouton]++;
            dico[chien]++;
            DisplayDico(dico);

            //on crée un nouveau chien (qui a les mêmes données que le premier, mais la référence n'est pas la même)
            Nounours chien2 = new Nounours("chien", new DateTime(2007, 06, 05), 1500);

            //chien2 est trouvé dans le dictionnaire car chien2 == chien, d'après le protocole d'égalité
            //(même si les références sont différentes)
            WriteLine(dico.ContainsKey(chien2));
            if (dico.ContainsKey(chien2))
            {
                dico[chien2]++;
            }
            else
            {
                dico.Add(chien2, 1);
            }
            DisplayDico(dico);
        }

        static void DisplayDico(Dictionary<Nounours, int> dico)
        {
            WriteLine("**********************");
            foreach (KeyValuePair<Nounours, int> pair in dico)
            {
                WriteLine($"{pair.Key.Name}   {pair.Value}");
            }
            WriteLine("**********************");
        }
    }
}
