C++

Класс Матрица, описывающий двумерный массив

Написать класс Матрица (в данном случае матрица – массив объектов класса Массив из предыдущего задания).

В классе реализовать следующие методы:

конструкторы (по умолчанию, с параметрами, копирования;
деструктор;
ввод с клавиатуры, вывод на экран (в виде методов класса и при помощи перегруженных операций потокового ввода и вывода);
поиск элемента по ключу.
В этом же классе, перегрузить операции:

+, += (сложение матриц);
– (вычитание);
= (присвоение);
== (сравнение по элементам);
[] (взятие элемента с заданным индексом).

Решение:

Заголовочный файл matrix.h класса Matrix.
#ifndef MATRIX_H
#define MATRIX_H
 
#include "array.h"
 
class Matrix
{
    friend ostream &operator<< (ostream &, const Matrix &); // перегруженный оператор вывода
    friend istream &operator>> (istream &, Matrix &); // перегруженный оператор ввода
private:
    Array *ptr; // указатель на матрицу типа Array
    int size; // размер матрицы
 
public:
    Matrix();// конструктор по умолчанию
    Matrix(int, int ); // конструктор с параметрами
    Matrix( Matrix &matrixToCopy ); // конструктор копии
    ~Matrix(); // десструктор класса Matrix
 
    int getSize() const; // возвратить количество объектов типа Array
    Array *getPtr() const; // вернуть указатель на объект типа Array
    Array &operator[] (int ); // перегруженная операция взятия индекса
    void setMatrix(); // заполнение матрицы
    void getMatrix(); // вывод матрицы
    int *search(const int key) const; // поиск по ключу
    Matrix operator+ (const Matrix &right);
    Matrix operator+= (const Matrix &right);
    Matrix operator- (const Matrix &right);
    const Matrix &operator= (const Matrix &right); // оператор присваивания
    bool operator== (const Matrix &right) const;// оператор сравнения
};
 
#endif // MATRIX_H

Исполняемый файл matrix.cpp класса Matrix.
#include "matrix.h"
 
#include "array.h"
 
#include <iostream>
using std::cout; // пространство имен std для cout
using std::cin; // пространство имен std для cin
 
#include <iomanip> // для манипулятора setw
using std::setw;   // пространство имен std для setw
 
#include <cstdlib>
 
Matrix::Matrix() // конструктор по умолчанию
{
    size = 10; // по умолчанию размер матрицы = 10 объектам типа Array
    ptr = new Array [size]; // выделить место в памяти для матрицы
    for (int ix = 0; ix < size; ix++) // обнуляем матрицу
        for (int jx = 0; jx < 10; jx++)
            ptr[ix][jx] = 0;
}
 
Matrix::Matrix(int matrixSize, int arraySize) // конструктор с параметрами
{
    size = (matrixSize > 0 ? matrixSize : 10); // количество строк
 
    ptr = new Array [size]; // выделить место в памяти для матрицы
 
    for (int ix = 0; ix < size; ix++) // перераспределяем выделенную память
        ptr[ix].setSize(arraySize > 0 ? arraySize : 10); // количество столбцов
 
    for (int ix = 0; ix < size; ix++) // обнуляем матрицу
        for (int jx = 0; jx < ptr->getSize(); jx++)
            ptr[ix][jx] = 0;
}
 
Matrix::Matrix(  Matrix &matrixToCopy ) // конструктор копии
    :size(matrixToCopy.size)              // инициализатор размера массива
{
    ptr = new Array [size]; // выделить место в памяти для матрицы
 
    for (int ix = 0; ix < size; ix++) // перераспределяем выделенную память
        ptr[ix].setSize(size); // количество столбцов
 
    for (int ix = 0; ix < size; ix++)
        for (int jx = 0; jx < ptr->getSize(); jx++)
            ptr[ix][jx] = matrixToCopy[ix][jx];// заполняем матрицу значениями матрицы matrixToCopy
}
 
Matrix::~Matrix() // десструктор класса Matrix
{
   delete  [] ptr; // освободить память, удалив матрицу
}
 
int Matrix::getSize() const // возвратить количество элементов матрицы
{
    return size;
}
 
Array *Matrix::getPtr() const
{
    return ptr;
}
 
// перегруженный оператор вывода для класса Array (вывод элементов массива на экран)
ostream &operator<< (ostream &output, const Matrix &obj)
{
    for (int ix = 0; ix < obj.size; ix++)
    {
        for (int jx = 0; jx < obj.ptr->getSize(); jx++)
        {
            output << setw(5) // под каждое число выделяется 5 позиций
                   << obj.ptr[ix][jx];
        }
        cout << std::endl;
    }
 
    output << std::endl; // перенос маркера на новую строку
 
    return output; // позволяет множественный вывод, типа cout << x << y << z << ...
}
 
// перегруженный оператор ввода, для заполнения матрицы с клавиатуры
istream &operator>> (istream & input, Matrix &obj)
{
    for (int ix = 0; ix < obj.size; ix++)
        for (int jx = 0; jx < obj.ptr->getSize(); jx++)
            input >> obj.ptr[ix][jx]; // заполняем матрицу
 
    return input; // позволяет множественный ввод, типа cin >> x >> y >> z >> ...
}
 
// перегруженный оператор взятия индекса
Array &Matrix::operator[] (int subscript)
{
    if(subscript < 0 || subscript >= size)
    {
        std::cerr << "\n Ошибка индекса: " << subscript << std::endl;
        exit(1); // завершить работу программы, неправильный индекс
    }
    return ptr[subscript]; // возврат ссылки на элемент массива
}
 
void Matrix::setMatrix() // заполнение массива
{
    for (int ix = 0; ix < size; ix++)
        for (int jx = 0; jx < ptr->getSize(); jx++)
            cin >> ptr[ix][jx]; // ввод элементов матрицы с клавиатуры
}
 
void Matrix::getMatrix() // вывод массива
{
    for (int ix = 0; ix < size; ix++)
    {
        for (int jx = 0; jx < ptr->getSize(); jx++)
            cout << setw(5) << ptr[ix][jx]; // вывод элементов матрицы на экран
        cout << std::endl;
    }
 
    cout << std::endl; // новая строка
}
 
int *Matrix::search(const int key) const // поиск по ключу
{
    for (int ix = 0; ix < size; ix++)
        for (int jx = 0; jx < ptr->getSize(); jx++)
            if ( key == ptr[ix][jx] ) // поиск по ключу
                return (&ptr[ix][jx]);             // позиция искомого элемента
 
    return NULL;
}
 
Matrix Matrix::operator+ (const Matrix &right)
{
    if (size != right.size || ptr->getSize() != right.getPtr()->getSize())
    {
        cout << "Массивы разного размера!\n";
        exit(1); // завершить работу программы
    }
 
    Matrix result(size, ptr->getSize());
    for (int ix = 0; ix < size; ix++)
        for (int jx = 0; jx < ptr->getSize(); jx++)
            result.ptr[ix][jx] = ptr[ix][jx] + right.ptr[ix][jx];
 
    return result; // вернуть сумму
}
 
Matrix Matrix::operator+= (const Matrix &right)
{
    if (size != right.size || ptr->getSize() != right.getPtr()->getSize())
    {
        cout << "Массивы разного размера!\n";
        exit(1); // завершить работу программы
    }
 
//    Matrix result(size, ptr->getSize());
    for (int ix = 0; ix < size; ix++)
        for (int jx = 0; jx < ptr->getSize(); jx++)
            ptr[ix][jx] = ptr[ix][jx] + right.ptr[ix][jx];
 
    return *this; // вернуть сумму
}
 
Matrix Matrix::operator- (const Matrix &right)
{
    if (size != right.size || ptr->getSize() != right.getPtr()->getSize())
    {
        cout << "Массивы разного размера!\n";
        exit(1); // завершить работу программы
    }
 
    Matrix result(size, ptr->getSize());
    for (int ix = 0; ix < size; ix++)
        for (int jx = 0; jx < ptr->getSize(); jx++)
            result.ptr[ix][jx] = ptr[ix][jx] - right.ptr[ix][jx];
 
    return result; // вернуть сумму
}
 
const Matrix &Matrix::operator= (const Matrix &right) // оператор присваивания
{
    if (&right != this) // чтобы не выполнялось самоприсваивание
    {
        if (size != right.size || ptr->getSize() != right.getPtr()->getSize())
        {
            delete [] ptr; // освободить пространство
            size = right.size; // установить нужный размер матрицы
            ptr = new Array [size]; // выделить память под копируемый массив
 
            for (int ix = 0; ix < size; ix++) // перераспределяем выделенную память
                ptr[ix].setSize(right.getPtr()->getSize()); // количество столбцов
        }
 
        for (int ix = 0; ix < size; ix++)
            for (int jx = 0; jx < ptr->getSize(); jx++)
                ptr[ix][jx] = right.ptr[ix][jx]; // скопировать массив
    }
 
    return *this; // разрешает множественное присваивание, например x = t = e
}
 
bool Matrix::operator== (const Matrix &right) const// оператор сравнения
{
    if (size != right.size || ptr->getSize() != right.getPtr()->getSize())
        return false; // матрицы с разным количеством элементов
 
    for (int ix = 0; ix < size; ix++)
        for (int jx = 0; jx < ptr->getSize(); jx++)
            if (ptr[ix][jx] != right.ptr[ix][jx])
                return false; // матрицы не равны
 
    return true; // матрицы равны
}

Файл с функцией main(). В этом файле я постарался протестировать все возможности класса Matrix.
#include <iostream>
using namespace std;
 
#include "matrix.h"
 
#include <cstdlib>
 
int main()
{
    srand(time(NULL));
    Matrix myMatrix1(5,5); // конструктор с параметрами
 
    // заполнение матрицы
    for (int ix = 0; ix < myMatrix1.getSize(); ix++)
        for (int jx = 0; jx < myMatrix1.getPtr()->getSize(); jx++)
            myMatrix1[ix][jx] = rand() % 100;
 
    cout << myMatrix1;  // перегруженный оператор вывода
 
    Matrix myMatrix2(myMatrix1); // конструктор копии
 
    myMatrix2.getMatrix(); // вывод матрицы с помощью метода класса Matrix
 
    //myMatrix2.setMatrix(); // заполнение матрицы с помощью метода класса Matrix
 
    int * adr = myMatrix2.search(99);
 
    if (adr == NULL)
        cout << "Значения " << 99 << " в матрице нет!\n";
    else
        cout << "Значение " << 99 << " находится в памяти по адресу: " << adr << endl;
 
    cout << (myMatrix1 + myMatrix2); // перегруженная операция сложения
 
    cout << "Как видите, myMatrix1 осталась без изменения!\n";
    cout << myMatrix1;
 
    myMatrix1 += myMatrix2; // перегруженная операция сложения-присвоения
 
    cout << "myMatrix1 содержит значения ,полученные при: myMatrix1 += myMatrix2; !\n";
    cout << myMatrix1;
 
    cout << (myMatrix1 - myMatrix1); // перегруженная операция вычитания
 
    Matrix myMatrix3 = myMatrix2; // перегруженная операция присваивания
 
    cout << myMatrix3;
 
    if (myMatrix3 == myMatrix2)
        cout << "Матрицы myMatrix3 и myMatrix2 равны!\n";
 
    return 0;
}
Теги:
Матрица, массив
Добавлено: 06 Апреля 2018 21:18:04 Добавил: Андрей Ковальчук Нравится 0
Добавить
Комментарии:
Нету комментариев для вывода...