Хочешь чуда? Будь чудом!
В общем коротко о сути проблемы:
Приспичило мне написать консольную версию Сапёра на C++ 5.02

Все хорошо, кроме одного:
В оригинале, когда открываешь пустую клетку - открываются все соседние пустые клетки вплоть до клеток с цифрами. Коряво объяснил - но суть, уверен, понятна.
Это легче всего в мозгу мне приходит в голову в виде рекурсии.
читать дальше

@темы: C++

Комментарии
02.09.2010 в 20:00

Хочешь чуда? Будь чудом!
Загоняйте в компилятор - он вам всё расскажет ).

Желательно if (a[x][y] == -1) return; в начале поставить, для читаемости например.


ага, спасибо большое.
да - надеюсь с компиллятором проблем не будет =)
04.09.2010 в 19:13

Хочешь чуда? Будь чудом!
Слушатель
Спасибо огромное. Всё работает отлично.
04.09.2010 в 19:37

Don't stop the music.
Catch By Madness
Рад слышать ). Удачи в дальнейшей деятельности ).
04.09.2010 в 20:48

Хочешь чуда? Будь чудом!
спасибо =)
05.09.2010 в 16:23

Хочешь чуда? Будь чудом!
Слушатель , вот еще спросить хотел:
вот в моей программе я использовал два массива:
1) числовой (в нем 9 - это мины а все остальные числа - кол-во мин вокруг считаются сразу после создаия массива и расстановки бомб)
2) символьный (собственно само поле)

первый массив я использовал для того, чтобы проверять наличие мины на данной клетке или количества мин.
все остальное было на втором массиве. В частности постановка/снятие флажка (когда нажимаешь кнопку "поставить/снять флажок", проверяю, что находится в этой клетке и после этого выбираю нужный вариант из двух...)

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

Но тут такая проблема. Проблема с постановкой/снятием флажков.

Пусть у меня маасив (поле) состоит изначально из символов ' ' и 'B'. ну, логично.
Поставить/снять флажок в таком случае не проблема, я это все беру из своего готового варианта.
Но есть вероятность "потерять" где находится мина, если поставить два флажка: один на мину, а другой не на мину.
Блин... Криво объясняю...

Или может просто создать двумерный массив с координатами мин, а все остальное считать уже по ходу?..

Просто вот задумался...
06.09.2010 в 07:13

Don't stop the music.
Catch By Madness
потому что у меня после каждого хода ВСЁ поле банально обновлялось
Покажите код, где у вас после очередного хода обновляется массив c.

Но есть вероятность "потерять" где находится мина, если поставить два флажка: один на мину, а другой не на мину.
Совершенно верно. Если мы заменим мину флажком (доска то у нас теперь одна), то фактически мы изменили изначальное состояние игры. А проверять перед тем как поставить флажок - есть там мина или нет, и если нет - не ставить - противоречит правилам игры. Советую не смешивать данные (числовая доска) с выводом (символьная доска).

Теперь: действительно в данном виде данные (изначальное состояние доски) представлены наглядно но громоздко, с помощью примитивной структуры - двумерный массив. Насколько я понял, вы хотите оптимизировать представление данных задав их не с помощью числового массива, а с помощью списка координат мин. Это чревато тем что:

У нас потеряна индексация элементов. То есть: для ввода (x, y) раньше мы просто смотрели a[x][y], и эта операция просмотра была быстрой. Теперь мы должна будем найти этот (x, y) в списке {(x0, y0), (x1, y1), ... (xk, yk)} где k - кол-во бомб. Эта операция пробега по списку в худшем случае (вся доска заполнена бомбами и мы ищем последнюю) берёт больше времени и столько же памяти сколько и массив. Вопрос - что мы выиграли с такой структурой?

Если же вы хотите создать двумерный массив с координатами мин то то что я читаю это следующее:
a[0][0] = (bombXCoord0, bombYCoord0)
a[0][1] = (bombXCoord1, bombYCoord1)
...
a[k][l] = (bombXCoordt, bombYCoordt)

где t - кол-во бомб. Вопрос - зачем это делать? У нас нет никакой связи между координатами массива (k, l) и координатами бомбы в нём. А если и есть, то зачем нам пихать в (k, l) саму координату бомбы?

Таким образом, перед нами проблема растраты памяти (например для доски 100x100 где всего навсего 5 бомб - мы выделяем массив 100x100). Эффективное решение такой проблемы существует при более сложных структурах данных, но сначала вам необходимо освоить и приобрести навыки программирования и работы с самим языком (ставя и решая различные задачи).
06.09.2010 в 17:55

Хочешь чуда? Будь чудом!
Насчет вывода. Вот такая ф-ия у меня для вывода ВСЕГО поля на экран. Я ф-ию Output вызываю после каждого действия (например: нажал на клавишу открытия клетки, клетка открылась [изменилось значение соответвующей ячейки], поле обновилось):

void Output()
{
for(int i=0;iА если и есть, то зачем нам пихать в (k, l) саму координату бомбы?
чтобы где-то "запомнить" координаты всех мин.

Эффективное решение такой проблемы существует при более сложных структурах данных, но сначала вам необходимо освоить и приобрести навыки программирования и работы с самим языком
хорошо, тогда откажусь от своих "гениальных" идей =)
06.09.2010 в 18:39

Don't stop the music.
хорошо, тогда откажусь от своих "гениальных" идей =)
Ни в коем случае этого не делайте. Это очень хорошо, что вы не остановились на достигнутом и продолжаете "крутить" проблему так и эдак. Такой "исcледовательский зуд" очень поможет вам в дальнейшем. Сам факт того, что вы вышли на проблему выше вашего уровня - это замечательно. Решение придёт - когда вы его достигнете.
06.09.2010 в 18:54

Хочешь чуда? Будь чудом!
Решение придёт - когда вы его достигнете.
=)

Спасибо))