Beispiel #1
0
        /// <summary>
        /// Returns all the children of a given MDD node that have a heuristic estimate that is not larger than the given heuristic bound.
        /// </summary>
        /// <param name="mdd"></param>
        /// <param name="heuristicBound">The heuristic estimate of the returned children must be lower than or equal to the bound</param>
        /// <param name="numOfAgents">The number of agents in the MDD node</param>
        /// <returns>A list of relevant MDD nodes</returns>
        private List <MDDNode> GetAllChildren(MDDNode father, int heuristicBound, int numOfAgents)
        {
            var children = new List <MDDNode>();

            foreach (TimedMove move in father.move.GetNextMoves())
            {
                if (this.problem.IsValid(move) &&
                    this.problem.GetSingleAgentOptimalCost(this.agentNum, move) <= heuristicBound) // Only nodes that can reach the goal in the given cost according to the heuristic.
                {
                    if (this.constraints != null)
                    {
                        queryConstraint.Init(agentNum, move);

                        if (this.constraints.Contains(queryConstraint))
                        {
                            continue;
                        }
                    }

                    if (this.mustConstraints != null && move.time < this.mustConstraints.Length && // There may be a constraint on the timestep of the generated node
                        this.mustConstraints[move.time] != null &&
                        this.mustConstraints[move.time].ContainsKey(this.agentNum))                // This agent has a must constraint for this time step
                    {
                        if (this.mustConstraints[move.time][this.agentNum].Equals(move) == false)
                        {
                            continue;
                        }
                    }

                    MDDNode child = new MDDNode(move, numOfAgents, this, this.supportPruning);
                    children.Add(child);
                }
            }
            return(children);
        }
Beispiel #2
0
        /// <summary>
        /// Check if the move is valid, i.e. not colliding into walls or other agents.
        /// This method is here instead of in ProblemInstance to enable algorithmic tweaks.
        /// </summary>
        /// <param name="possibleMove">The move to check if possible</param>
        /// <returns>true, if the move is possible.</returns>
        protected bool IsValid(TimedMove possibleMove, HashSet <TimedMove> currentMoves, int makespan, int agentNum)
        {
            // Check if the proposed move is reserved in the plan of another agent.
            // This is used in Trevor's IndependenceDetection.
            if (this.illegalMoves != null)
            {
                if (possibleMove.IsColliding(illegalMoves))
                {
                    return(false);
                }
            } // FIXME: Also checked in instance.IsValid later.

            if (this.constraintList != null)
            {
                queryConstraint.Init(agentNum, possibleMove);

                if (this.constraintList.Contains(queryConstraint))
                {
                    return(false);
                }
            }

            if (this.mustConstraints != null && makespan < this.mustConstraints.Length && // There may be a constraint on the timestep of the generated node
                this.mustConstraints[makespan] != null)
            {
                if (this.mustConstraints[makespan].Any <CbsConstraint>(
                        con => con.ViolatesMustConstraint((byte)agentNum, possibleMove)))
                {
                    return(false);
                }
            }

            // If the tile is not free (out of the grid or with an obstacle)
            if (this.instance.IsValid(possibleMove) == false)
            {
                return(false);
            }

            // Check against all the agents that have already moved to see if current move collides with their move
            return(possibleMove.IsColliding(currentMoves) == false);
        }