C#. Розробка узагальненого класу, що містить засоби реалізації лінійного пошуку елементу в масиві




Розробка узагальненого класу, що містить засоби реалізації лінійного пошуку елементу в масиві

У даній темі демонструється покроковий процес розробки класу LSearch<T>, який містить ряд методів що реалізують лінійний пошук елементу (ключа) в одновимірному масиві елементів, що мають тип T. Пройшовши всі пункти даної теми можна отримати досвід з розробки класів мовою C# та вивчення основ об’єктно-орієнтованого програмування.


Зміст


Пошук на інших ресурсах:

Умова задачі

Використовуючи засоби мови C# розробити клас LSearch<T>, який містить методи, що здійснюють пошук заданого ключа в одновимірному масиві. У класі реалізувати:

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

 

Виконання

1. Створення додатку типу Console Application. Структура проекту

Початковий код модуля, що включає класи LSearch<T> та Program наступний

using static System.Console;

namespace ConsoleApp1
{
  // Клас обробляє узагальнений тип T
  class LSearch<T>
  {

  }

  class Program
  {
    static void Main(string[] args)
    {

    }
  }
}

 

2. Розробка узагальненого класу LSearch<T>
2.1. Внутрішні змінні класу

Лінійний пошук реалізується в одновимірному масиві. Тому, в клас LSearch<T> включається одновимірний масив типу T

...

class LSearch<T>
{
  // Внутрішні змінні класу
  private T[] A; // Одновимірний масив
}

...

 

2.2. Конструктори класу

У тіло класу LSearch<T> вводяться два конструктори:

  • конструктор без параметрів LSearch() – ініціалізує масив значенням null;
  • конструктор з параметром LSearch(T[]) – ініціалізує внутрішній масив A значеннями елементів іншого масиву. Для виділення пам’яті та копіювання даних в масив A використовується метод Clone(), який можна використовувати для всіх масивів.
// Конструктори класу.
// Конструктор без параметрів
public LSearch()
{
  A = null;
}

// Конструктор, який отримує вхідним масив елементів типу T
public LSearch(T[] _A)
{
  // Використати метод Clone()
  A = (T[])_A.Clone(); // скопіювати масив
}

 

2.3. Методи доступу до внутрішнього масиву

Для доступу до масиву A екземпляру класу LSearch<T> реалізовано наступні методи

// Методи доступу до масиву
// Отримати посилання на увесь масив
public T[] Get()
{
  return A;
}

// Встановити новий масив
public void Set(T[] _A)
{
  A = (T[])_A.Clone();
}

 

2.4. Методи реалізації лінійного пошуку
2.4.1. Метод IsItem(). Визначення наявності заданого елементу в масиві

Метод IsItem() визначає, чи взагалі є елемент в масиві. Метод має дві перевантажені реалізації. Перша реалізація здійснює пошук ключа (елементу) в зовнішньому масиві, що передається в метод вхідним параметром. Друга реалізація використовує внутрішній масив A.

// Методи, що реалізують лінійний пошук
// Визначення наявності заданого елементу в масиві
public bool IsItem(T[] A, T key)
{
  for (int i = 0; i < A.Length; i++)
    if (A[i].Equals(key)) // перевірка, чи значення об'єктів рівні
      return true;
  return false;
}

// Перевантажений варіант методу IsItem, в якому обробляється внутрішній масив.
public bool IsItem(T key)
{
  return IsItem(this.A, key);
}

 

2.4.2. Метод GetNOccurences(). Визначення кількості входжень заданого елементу в масиві

Метод GetNOccurences() повертає кількість входжень заданого елементу в масиві. Метод виконує послідовне сканування масиву з початку до кінця та порівнює вхідний ключ (елемент) key з кожним елементом масиву. Для порівняння використовується метод Equals() класу System.Object.

// Визначення кількості входжень елементу в масиві
// Реалізація методу для будь-якого зовнішнього масиву
public int GetNOccurences(T[] A, T key)
{
  int k = 0;
  for (int i = 0; i < A.Length; i++)
    if (A[i].Equals(key))
      k++;
  return k;
}

// Реалізація методу для внутрішнього масиву
public int GetNOccurences(T key)
{
  return GetNOccurences(this.A, key);
}

 

2.4.3. Метод GetPositions(). Отримати масив позицій входження заданого елементу в масиві

З допомогою перевантаженого методу GetPositions() можна отримати масив, що містить номери позицій в яких розміщується заданий ключ (елемент). У методі GetPositions() використовується метод CopyTo() для копіювання одного масиву в інший.

// Отримати масив позицій входження елементу в масиві
public int[] GetPositions(T[] A, T key)
{
  int[] AP = new int[0]; // на початку в масиві 0 елементів
  int[] AP2; // допоміжний масив

  for (int i = 0; i < A.Length; i++)
  {
    if (A[i].Equals(key))
    {
      // Виділити пам'ять для нового масиву на 1 елемент більше
      try
      {
        AP2 = new int[AP.Length + 1];

        // Скопіювати AP => AP2 - використати метод CopyTo()
        AP.CopyTo(AP2, 0);

        // Додати останній елемент
        AP2[AP.Length] = i;

        // Перенаправити посилання
        AP = AP2;
      }
      catch (Exception e)
      {
        WriteLine(e.Message);
      }
    }
  }

  return AP;
}

// Перевантажена версія методу GetPositions()
public int[] GetPositions(T key)
{
  return GetPositions(this.A, key);
}

 

2.5. Метод виведенння внутрішнього масиву

З метою тестування у клас LSearch<T> введено метод Print() роздруку внутрішнього масиву A на екран.

// Метод виведення масиву на екран
public void Print(string comment)
{
  WriteLine(comment);
  for (int i = 0; i < A.Length; i++)
    Write("{0}   ", A[i]);
  WriteLine();
}

 

2.6. Скорочений текст класу LSearch<T>

Скорочений вигляд класу LSearch<T> наступний

// Розробка узагальненого класу, який містить засоби для реалізації лінійного пошуку.
// Клас обробляє узагальнений тип T
class LSearch<T>
{
  // Внутрішні змінні класу
  private T[] A; // Одновимірний масив

  // Конструктори класу.
  // Конструктор без параметрів
  public LSearch()
  {
    ...
  }

  // Конструктор, який отримує вхідним масив елементів типу T
  public LSearch(T[] _A)
  {
    ...
  }

  // Методи доступу до масиву
  // Отримати посилання на увесь масив
  public T[] Get()
  {
    ...
  }

  // Встановити новий масив
  public void Set(T[] _A)
  {
    ...
  }

  // Методи, що реалізують лінійний пошук
  // Визначення наявності заданого елементу в масиві
  public bool IsItem(T[] A, T key)
  {
    ...
  }

  // Перевантажений варіант методу IsItem, в якому обробляється внутрішній масив.
  public bool IsItem(T key)
  {
    ...
  }

  // Визначення кількості входжень елементу в масиві
  // Реалізація методу для будь-якого зовнішнього масиву
  public int GetNOccurences(T[] A, T key)
  {
    ...
  }

  // Реалізація методу для внутрішнього масиву
  public int GetNOccurences(T key)
  {
    ...
  }

  // Отримати масив позицій входження елементу в масиві
  public int[] GetPositions(T[] A, T key)
  {
    ...
  }

  // Перевантажена версія методу GetPositions()
  public int[] GetPositions(T key)
  {
    ...
  }

  // Метод виведення масиву на екран
  public void Print(string comment)
  {
    ...
  }
}

 

3. Тестування роботи класу LSearch<T>. Метод main()

Робота класу тестується в методі main(), який розміщений в класі Program.

class Program
{
  static void Main(string[] args)
  {
    // Тестування класу LSearch<T>
    int[] AI = { 5, 8, 9, -1, 4 };

    // Створити екземпляр класу LSearch<int> з заданим масивом AI
    LSearch<int> L1 = new LSearch<int>(AI);

    // Визначити, чи є елемент 8. Метод IsItem()
    if (L1.IsItem(8))
      WriteLine("Item 8 is in array AI");
    else
      WriteLine("Item 8 is not in array AI");

    // Тестування методу GetNOccurences()
    char[] AC = { 'a', 'b', 'f', 'a', 'a', 'c', 'd', 'i', 'f' };
    LSearch<char> L2 = new LSearch<char>(AC);
    int n = L2.GetNOccurences('a');
    WriteLine("n = {0}", n); // n = 3

    // Тестування методу GetPositions()
    bool[] AB = { true, true, false, false, true, false, true, true }; // масив
    LSearch<bool> L3 = new LSearch<bool>(); // викликається конструктор без параметрів
    L3.Set(AB); // Метод Set() - встановити новий масив
    int[] Positions = L3.GetPositions(true);

    // Вивести позиції значення true в масиві AB
    for (int i = 0; i < Positions.Length; i++)
    {
      Write("{0}   ", Positions[i]);
    }
    WriteLine();
    ReadLine();
  }
}

Після запуску на виконання програма видає наступний результат

Item 8 is in array AI
n = 3
0 1 4 6 7

 


Зв’язані теми