/// <summary> /// Заполняет поле псевдослучайными числами. /// </summary> private void generate(RandomLocker rnd) { bool[,] used = new bool[9, 9]; Iterator root = new Iterator(used, cells, 81, rnd); root.startGenerate(); }
private void createOfVoids(int Voids, RandomLocker rnd) { void r90(ref int x, ref int y) { int buf = 8 - y; y = x; x = buf; } int n4 = Voids / 4; int rest = Voids % 4; if (rest % 2 == 1) { cells[4, 4].Value = 0; } for (int i = 0; i < n4; i++) { int x, y; do { x = rnd.Next() % 9; y = rnd.Next() % 9; } while ((x == 4 && y == 4) || cells[x, y].Value == 0); cells[x, y].Value = 0; r90(ref x, ref y); cells[x, y].Value = 0; r90(ref x, ref y); cells[x, y].Value = 0; r90(ref x, ref y); cells[x, y].Value = 0; } if (rest / 2 == 1) { int x, y; do { x = rnd.Next() % 9; y = rnd.Next() % 9; } while ((x == 4 && y == 4) || cells[x, y].Value == 0); cells[x, y].Value = 0; r90(ref x, ref y); r90(ref x, ref y); cells[x, y].Value = 0; } }
/// <summary> /// Инициализирует новую игру с указанным числом пустот /// </summary> /// <param name="amountOfVoids"></param> /// <param name="rnd"></param> public void initGame(int amountOfVoids, RandomLocker rnd) { // Снимаем фиксацию for (int x = 0; x < 9; x++) { for (int y = 0; y < 9; y++) { cells[x, y].Fixed = false; cells[x, y].Value = 0; } } // Оставляем число подсказок в допустимых пределах if (amountOfVoids > 65) { amountOfVoids = 65; } else if (amountOfVoids < 0) { amountOfVoids = 0; } // Генерируем поле generate(rnd); // Расставляем пустоты createOfVoids(amountOfVoids, rnd); voidCellAmount = 81; // Фиксируем непустые ячейки for (int x = 0; x < 9; x++) { for (int y = 0; y < 9; y++) { if (cells[x, y].Value != 0) { cells[x, y].Fixed = true; voidCellAmount--; } } } }
// Нужен здесь для экономии времени на выделение/освобождение памяти /// <summary> /// Создаёт новый ряд итераторов идущих друг за другом /// </summary> /// <param name="used">Массив использования ячеек</param> /// <param name="cells">Массив ячеек</param> /// <param name="amount">Количество итераторов (Длинна ряда)</param> /// <param name="rnd">Генератор случайных чисел (Зачем он здесь нужен...)</param> internal Iterator(bool[,] used, Cell[,] cells, int amount, RandomLocker rnd) { // Процесс подбора случайной свободной ячейки из верхней линии int x, y; y = 8 - ((amount - 1) / 9); do { x = rnd.Next() % 9; } while (used[x, y]); // Когда нашли свободную cell = cells[x, y]; // Забираем used[x, y] = true; // себе // При условии, что мы не опустились до еденицы, создаём следующий итератор // И передаём остатки if (amount > 1) { next = new Iterator(used, cells, amount - 1, rnd); } }