C#. Робота з множинами. 

Опорний конспект

Множина – це колекція, яка реалізує основні математичні операції над множинами: перетини (intersection), об’єднання (union), різниця (difference) і симетрична різниця (symmetric difference).

Множина - це набір деяких об'єктів, не впорядкований набір даних, що повторюються.

Приклади: 

  1. Цілі числа: [1,4,67,34,5]
  2. Символи типу char: [‘G’, ’!’, ‘o’]
  3. Великі та малі латинські літери (діапазон символів): [‘A’…’Z’, ’a’…’z’]

У математиці множини – це колекції об’єктів, у яких є щось спільне. 
Наприклад, ми можемо оголосити множину парних додатних цілих чисел: [2, 4, 6, 8, 10, ...]
Чи множину непарних додатних цілих: [1, 3, 5, 7, 9, ...]
У цих двох множинах немає спільних елементів. 
Давайте тепер подивимося на множину дільників числа 100: [1, 2, 4, 5, 10, 20, 25, 50, 100]
Тепер ми можемо дізнатися, які дільники числа 100 – непарні, просто дивлячись на множину непарних чисел і на множину дільників, вибираючи ті з чисел, які є в обох. 
Ми також можемо відповісти на запитання: “Які непарні числа не є дільниками ста”? чи “Які додатні цілі парні або непарні, не є дільниками ста?”.
На перший погляд це видається не дуже корисним, але це штучний приклад. Припустимо, що у нас є множина всіх працівників підприємства і множина працівників, які пройшли щомісячну перевірку. Тоді ми легко зможемо відповісти на запитання: “Хто з працівників не пройшов перевірку?”.

В C# є такі типи множин:

  • Послідовності
  • Колекції
  • Списки
  • Словники

Ці типи задаються інтерфейсами IEnumerable<T>, ICollection<T>, IList<T>, IDictionary<K, V> (відповідно).

Колекція, що містить тільки відрізняються елементи, називається множиною (set).  У складі .NET 4 є дві множини - HashSet <T> і SortedSet <T>. Обидві вони реалізують інтерфейс ISet <T>. Клас HashSet <T> містить невпорядкований список розрізняються елементів, а в SortedSet <T> елементи впорядковані.

Інтерфейс ISet <T> надає методи для створення об'єднання кількох множин, перетину множин і визначення, чи є одне множина надмножиною або підмножиною іншого.
Клас Set
Клас Set реалізує інтерфейс IEnumerable і приймає аргумент типу, який є спадкоємцем IComparable, оскільки для роботи алгоритмів потрібна перевірка елементів на рівність.
Метод Add
Дія: додає елементи у множину.
Метод AddRange
Дія: додає декілька елементів у множину. 
Метод Remove
Дія: видаляє вказаний елемент з множини і повертає true. У разі, якщо елемента немає, повертає false.
Метод Contains
Дія: повертає true, якщо множина містить вказаний елемент. Якщо ні, то повертає false.
Метод Count
Дія: повертає кількість елементів великої кількості або 0, якщо множина порожня.

Методи для роботи з множинами:

  • Різниця
  • Об'єднання
  • Перетин

Різниця множин

За допомогою методу Except можна отримати різницю двох множин:

string[] soft = { "Microsoft", "Google", "Apple"};

string[] hard = { "Apple", "IBM", "Samsung"};

 // різниця множин

var result = soft.Except(hard);

 foreach (string s in result)

Console.WriteLine(s);

В даному випадку з масиву soft забираються всі елементи, які є в масиві hard. Результатом операції будуть два елементи: Microsoft, Google.

Перетин множин

Для отримання перетину множин, тобто загальних для обох наборів елементів, застосовується метод Intersect:

string[] soft = { "Microsoft", "Google", "Apple"};

string[] hard = { "Apple", "IBM", "Samsung"};

 // перетин множин

var result = soft.Intersect(hard);

 foreach (string s in result)

    Console.WriteLine(s);

Так як обидва набори мають тільки один спільний елемент, то відповідно тільки він і потрапить в результуючу вибірку: Apple.

Об'єднання множин

Для об'єднання двох множин використовується метод Union. Його результатом є новий набір, в якому присутні елементи, як з однї, так і з другої множини. Повторювані елементи додаються в результат тільки один раз:

string[] soft = { "Microsoft", "Google", "Apple"};

string[] hard = { "Apple", "IBM", "Samsung"};

 // об'єднання множин

var result = soft.Union(hard);

 foreach (string s in result)

    Console.WriteLine(s);

Результатом операції буде набір: Microsoft, Google, Apple, IBM, Samsung.

До уваги!

Якщо нам потрібно просте об'єднання двох наборів, то ми можемо використовувати метод Concat: 

var result = soft.Concat (hard);

Ті елементи, які зустрічаються в обох наборах, дублюються.

Для видалення дублів в наборі використовується метод Distinct:

var result = soft.Concat (hard).Distinct ();

Опорні вправи

Створити дві множини, елементами якої є латинські букви. Проілюструвати операції над цими множинами з відповідними коментарями.

static void Main()
        {
            // Создадим два множества
            SortedSet<char> ss = new SortedSet<char>();
            SortedSet<char> ss1 = new SortedSet<char>();

            ss.Add('A');
            ss.Add('B');
            ss.Add('C');
            ss.Add('Z');
            ShowColl(ss, "Перша множина (колекцiя): ");

            ss1.Add('X');
            ss1.Add('Y');
            ss1.Add('Z');
            ShowColl(ss1, "Друга множина (колекцiя): ");

            ss.SymmetricExceptWith(ss1);
            ShowColl(ss, "Виключаємо одинаковi елементи двох множин: ");

            ss.UnionWith(ss1);
            ShowColl(ss, "Об'єднали множини: ");

            ss.ExceptWith(ss1);
            ShowColl(ss, "Вiднiмання множин");

            Console.ReadLine();
        }

        static void ShowColl(SortedSet<char> ss, string s)
        {
            Console.WriteLine(s);
            foreach (char ch in ss)
                Console.Write(ch + " ");
            Console.WriteLine("\n");
        }

Типова вправа

static void Main()
        {
            // Створюємо множини А і В
            SortedSet<char> A = new SortedSet<char>();
            SortedSet<char> B = new SortedSet<char>();

            A.Add('1');
            A.Add('3');
            A.Add('5');
            A.Add('7');
            ShowColl(A, "Множина А: ");

            B.Add('1');
            B.Add('5');
            B.Add('0');
            ShowColl(B, "Множина В: ");

            A.SymmetricExceptWith(B);
            ShowColl(A, "Перетин множин: ");

            A.UnionWith(B);
            ShowColl(A, "Об'єднання множини: ");

            A.ExceptWith(B);
            ShowColl(A, "Рiзниця множин");

            Console.ReadLine();
        }

        static void ShowColl(SortedSet<char> A, string s)
        {
            Console.WriteLine(s);
            foreach (char ch in A)
                Console.Write(ch + " ");
            Console.WriteLine("\n");
        }

Завдання для практичної роботи

Дано текст, записаний малими літерами української абетки. Надрукувати усі голосні літери цього тексту; усі приголосні літери; дзвінкі приголосні; глухі приголосні.

Голосні літери -  а, е, є, и, і, ї, о, у. ю, а; приголосні - усі решта літер окрім й, ь; дзвінкі приголосні - б, в, г, д, ж, з, л, м, н, р; глухі приголосні - л, п, с, т, ф, х, ц, ч, ш. щ.

Дано текст "я навчаюсь програмувати"