예제 #1
0
        private static void SplitTask(QueenTask baseTask, int numQueens, int levels, Queue <QueenTask> taskQueue)
        {
            // Base case for recursion.
            if (levels == 1)
            {
                baseTask.id = taskQueue.Count;
                taskQueue.Enqueue(baseTask);
                return;
            }

            for (int i = 0; i < numQueens; i++)
            {
                long queen = 1 << i;

                var subTask = baseTask;
                subTask.id = 0;                 // Will be set later.
                // No need to set masks[] as it is scratch for the task code.
                subTask.solutions = 0;
                subTask.step      = Step.Place;
                subTask.col       = (byte)(baseTask.col + 1);
                subTask.startCol  = (byte)(baseTask.col + 1);
                subTask.rook      = subTask.rook | queen;
                subTask.add      |= queen << baseTask.col;
                subTask.sub      |= queen << (numQueens - 1 - baseTask.col);
                subTask.mask      = ((1 << numQueens) - 1) & ~(subTask.rook | (subTask.add >> subTask.col) | (subTask.sub >> ((NumQueens - 1) - subTask.col)));

                if (Pop(subTask.rook) == subTask.col &&
                    Pop(subTask.add) == subTask.col &&
                    Pop(subTask.sub) == subTask.col)
                {
                    SplitTask(subTask, numQueens, levels - 1, taskQueue);
                }
            }
        }
예제 #2
0
        // For an instnace of the N-Queens problem of size n, get a list of QueenTask
        // tasks that covers the entire problem. That is, when each task is complete
        // the number of solutions found by each task can be summed to determine the
        // total number of solutions.
        private static Queue <QueenTask> GetQueenTaskPartition(int numQueens, int splitDepth)
        {
            var wholeProblemTask = new QueenTask();

            wholeProblemTask.mask = (1 << numQueens) - 1;

            var taskQueue = new Queue <QueenTask>();

            SplitTask(wholeProblemTask, numQueens, splitDepth, taskQueue);

            return(taskQueue);
        }
예제 #3
0
        // For an instnace of the N-Queens problem of size n, get a list of QueenTask
        // tasks that covers the entire problem. That is, when each task is complete
        // the number of solutions found by each task can be summed to determine the
        // total number of solutions.
        private static Queue<QueenTask> GetQueenTaskPartition(int numQueens, int splitDepth)
        {
            var wholeProblemTask = new QueenTask();
            wholeProblemTask.mask = (1 << numQueens) - 1;

            var taskQueue = new Queue<QueenTask>();

            SplitTask(wholeProblemTask, numQueens, splitDepth, taskQueue);

            return taskQueue;
        }
예제 #4
0
        private static void SplitTask(QueenTask baseTask, int numQueens, int levels, Queue<QueenTask> taskQueue)
        {
            // Base case for recursion.
            if (levels == 1)
            {
                baseTask.id = taskQueue.Count;
                taskQueue.Enqueue(baseTask);
                return;
            }

            for (int i = 0; i < numQueens; i++)
            {
                long queen = 1 << i;

                var subTask = baseTask;
                subTask.id = 0; // Will be set later.
                // No need to set masks[] as it is scratch for the task code.
                subTask.solutions = 0;
                subTask.step = Step.Place;
                subTask.col = (byte)(baseTask.col + 1);
                subTask.startCol = (byte)(baseTask.col + 1);
                subTask.rook = subTask.rook | queen;
                subTask.add |= queen << baseTask.col;
                subTask.sub |= queen << (numQueens - 1 - baseTask.col);
                subTask.mask = ((1 << numQueens) - 1) & ~(subTask.rook | (subTask.add >> subTask.col) | (subTask.sub >> ((NumQueens - 1) - subTask.col)));

                if (Pop(subTask.rook) == subTask.col &&
                    Pop(subTask.add) == subTask.col &&
                    Pop(subTask.sub) == subTask.col)
                {
                    SplitTask(subTask, numQueens, levels - 1, taskQueue);
                }
            }
        }
예제 #5
0
        private static QueenTask[] GetNextAssignment(QueenTask[] inProgress, Queue<QueenTask> todos, IList<QueenTask> done)
        {
            var nextAssignment = new List<QueenTask>();

            foreach (var task in inProgress)
            {
                if (task.step == Step.Done)
                {
                    done.Add(task);
                }
                else
                {
                    nextAssignment.Add(task);
                }
            }

            while (nextAssignment.Count < Spread && todos.Any())
                nextAssignment.Add(todos.Dequeue());

            return nextAssignment.ToArray();
        }