C++ was created by Bjarne Stroustrup as an extension to C.  C++ added classes, generics, and functional features to C.  C++ has lost a lot of popularity to newer languages, such as Python and Java, but still remains popular for systems programming and high performance game programming.

The code below has been tested with Microsoft Visual Studio 2019.

maze.cpp


#include 
#include 
#include 
#include 
struct Cell {
public:
	int row, column;
	bool north=false, south=false, east=false, west=false;
	bool visited=false;
};

class Maze {
	Cell** grid;  //holds a two dimentional array of cells
	int rows, columns; //the number of rows and columns

	static const int north = 0;
	static const int south = 1;
	static const int east = 2;
	static const int west = 3;

public:
	Maze(int rows, int columns)
	{
		this->rows = rows;
		this->columns = columns;
		grid = new Cell*[rows];
		for (int row = 0; row < rows; ++row) grid[row] = new Cell[columns];
		for (int row = 0; row < rows; ++row) {
			for (int column = 0; column < columns; ++column) {
				grid[row][column].row = row;
				grid[row][column].column = column;
			}
		}
		generate();
	}

	~Maze()
	{
		for (int row = 0; row < rows; ++row) delete[] grid[row];
		delete[] grid;
	}

	void generate()
	{
		std::vector stack;
		stack.push_back(grid[rand() % rows][rand() % columns]);
		stack.back().visited = true;
		while (!stack.empty()) {
			Cell cell = stack.back();
			std::vector directions = getDirections(cell);
			if (directions.size() != 0) {
				int direction = directions[rand() % directions.size()];
				switch (direction) {
				case north:
					grid[cell.row][cell.column].north = true;
					grid[cell.row - 1][cell.column].south = true;
					grid[cell.row - 1][cell.column].visited = true;
					stack.push_back(grid[cell.row - 1][cell.column]);
					break;
				case south:
					grid[cell.row][cell.column].south = true;
					grid[cell.row + 1][cell.column].north = true;
					grid[cell.row + 1][cell.column].visited = true;
					stack.push_back(grid[cell.row + 1][cell.column]);
					break;
				case east:
					grid[cell.row][cell.column].east = true;
					grid[cell.row][cell.column+1].west = true;
					grid[cell.row][cell.column+1].visited = true;
					stack.push_back(grid[cell.row][cell.column+1]);
					break;
				case west:
					grid[cell.row][cell.column].west = true;
					grid[cell.row][cell.column-1].east = true;
					grid[cell.row][cell.column-1].visited = true;
					stack.push_back(grid[cell.row][cell.column-1]);
					break;
				}
			}
			else {
				stack.pop_back();
			}
		}

	}

	std::vector getDirections(Cell cell)
	{
		std::vector directions;
		if ((cell.row > 0) && (!grid[cell.row - 1][cell.column].visited))
			directions.push_back(north);
		if ((cell.row < rows - 1) && (!grid[cell.row + 1][cell.column].visited))
			directions.push_back(south);
		if ((cell.column > 0) && (!grid[cell.row][cell.column - 1].visited))
			directions.push_back(west);
		if ((cell.column < columns - 1) && (!grid[cell.row][cell.column + 1].visited))
			directions.push_back(east);
		return directions;
	}

	friend std::ostream& operator<< (std::ostream& out, const Maze& point);

};

std::ostream& operator<< (std::ostream& out, const Maze& maze)
{
	out << "\n+";
	for (int column = 0; column < maze.columns; ++column)
		out << "--+";
	for (int row = 0; row < maze.rows; ++row) {
		out << "\n|";
		for (int column = 0; column < maze.columns; ++column)
			if (maze.grid[row][column].east)
				out << "   ";
			else
				out << "  |";
		out << "\n+";
		for (int column = 0; column < maze.columns; ++column)
			if (maze.grid[row][column].south)
				out << "  +";
			else
				out << "--+";
	}
	return out; // return std::ostream so we can chain calls to operator<<
}
int main()
{
	srand(time(NULL));
	int width, height;
	std::cout << "Width? ";
	std::cin >> width;
	std::cout << "\nHeight? ";
	std::cin >> height;
	Maze maze(height,width);
	std::cout << maze;
}