diff --git a/SolovevDS/docs/data/data_for_task2/task2.cpp b/SolovevDS/docs/data/data_for_task2/task2.cpp index 6e97642..002c785 100644 --- a/SolovevDS/docs/data/data_for_task2/task2.cpp +++ b/SolovevDS/docs/data/data_for_task2/task2.cpp @@ -1,3 +1,8 @@ +#include +#include +#include +#include + class cell{ private: int x, y; @@ -44,6 +49,21 @@ class maze{ cell* exit; public: + maze(int width, int height) + { + this->width = width; + this->height = height; + this->start = nullptr; + this->exit = nullptr; + + matrix = new cell*[width]; + + for (int x = 0; x < width; ++x) { + matrix[x] = new cell[height]; + for (int y = 0; y < height; ++y) + matrix[x][y] = cell(x, y, false, false, false); + } + } maze(int width, int height, int startX, int startY, int exitX, int exitY) { this->width = width; @@ -52,8 +72,13 @@ class maze{ this->exit = nullptr; matrix = new cell*[width]; - for (int i = 0; i < width; ++i) - matrix[i] = new cell[height]; + for (int x = 0; x < width; ++x) { + matrix[x] = new cell[height]; + for (int y = 0; y < height; ++y) { + matrix[x][y] = cell(x, y, false, false, false); + } + } + matrix[startX][startY].setStart(true); matrix[exitX][exitY].setExit(true); @@ -75,6 +100,18 @@ class maze{ return &matrix[x][y]; } + void setCell(int x, int y, cell newCell) { + if (x < 0 || x >= width || y < 0 || y >= height) + return; + + matrix[x][y] = newCell; + + if (matrix[x][y].getIsStart()) + start = &matrix[x][y]; + + if (matrix[x][y].getIsExit()) + exit = &matrix[x][y]; + } cell** getNeighbors(cell* current) { /*ДЕЛАТЬ delete[] neighbors; !!!!!!!!!!!!!!!*/ cell** neighbors = new cell*[5]; @@ -112,4 +149,110 @@ class maze{ cell* getStart() {return start;} cell* getExit() {return exit;} -}; \ No newline at end of file +}; + +class MazeBuilder { + public: + virtual maze* buildFromFile(const std::string& filename) = 0; + virtual ~MazeBuilder() {} +}; + +class TextFileMazeBuilder : public MazeBuilder { + public: + maze* buildFromFile(const std::string& filename) override + { + + std::ifstream file(filename); + if (!file.is_open()) + throw std::runtime_error("Ошибка: Не удалось открыть файл!"); + + std::string line; + int width = 0; + int height = 0; + + // ДОБАВИЛ: первый проход по файлу. + // Здесь узнаём ширину и высоту лабиринта. + while (std::getline(file, line)) { + if (height == 0) { + width = line.length(); + } + else { + if (line.length() != width) + throw std::runtime_error("Ошибка: строки лабиринта разной длины!"); + } + height++; + } + + if (width == 0 || height == 0) { + throw std::runtime_error("Ошибка: файл пустой!"); + } + + file.clear(); + file.seekg(0); + + maze* labirint = new maze(width, height); + bool hasStart = false; + bool hasExit = false; + int y = 0; + + + while (std::getline(file, line)) { + + for (int x = 0; x < width; x++) { + char ch = line[x]; + + bool isWall = false; + bool isStart = false; + bool isExit = false; + + switch(ch){ + case '#': + isWall = true; + break; + case ' ': + isWall = false; + break; + case 'S': + isStart = true; + + if (hasStart) + throw std::runtime_error("Ошибка: в лабиринте больше одного старта!"); + + hasStart = true; + break; + case 'E': + isExit = true; + + if (hasExit) + throw std::runtime_error("Ошибка: в лабиринте больше одного выхода!"); + hasExit = true; + break; + default: + throw std::runtime_error("Ошибка: неизвестный символ в файле!"); + break; + } + + cell current(x, y, isWall, isExit, isStart); + labirint->setCell(x, y, current); + } + + y++; + } + file.close(); + if (!hasStart) + throw std::runtime_error("Ошибка: в лабиринте нет старта!"); + if (!hasExit) + throw std::runtime_error("Ошибка: в лабиринте нет выхода!"); + return labirint; + + } + + // прочитать символы + // создать клетки + // вернуть готовый Maze + } +}; + +int main(){ + +} \ No newline at end of file