示例#1
0
        /// <summary>
        /// Ons the cost path changed impl.
        /// </summary>
        /// <param name="oldValue">Old value.</param>
        /// <param name="newValue">New value.</param>
        protected virtual void OnCostPathChangedImpl(TraversalPath oldValue, TraversalPath newValue)
        {
            var path        = CostPath ?? new TraversalPath(0);
            var columnCount = path.RowIndices.Length;

            //reset all cells
            foreach (View view in Children)
            {
                var cell          = (MatrixCell)view;
                var currentColumn = cell.Column;
                var currentRow    = cell.Row + 1;

                var pathMatch = (currentColumn < columnCount) &&
                                (path.RowIndices[currentColumn] == currentRow);

                if (pathMatch)
                {
                    cell.IsPartOfLowestCostPath = true;
                    cell.IsPathValid            = path.IsValid;
                }
                else
                {
                    cell.IsPartOfLowestCostPath = false;
                    cell.IsPathValid            = true;
                }
            }
        }
示例#2
0
        /// <summary>
        /// Prints the traversal path.
        /// </summary>
        /// <param name="lowestPath">Lowest path.</param>
        static void PrintTraversalPath(TraversalPath lowestPath)
        {
            Console.WriteLine();

            Console.ForegroundColor = MSG_COLOR;
            Console.WriteLine("Result: ");

            Console.ForegroundColor = OUTPUT_COLOR;
            Console.WriteLine(lowestPath.ToString());
        }
        /// <summary>
        /// Computes the lowest cost path, in recursive manner.
        /// </summary>
        /// <returns>Calculate the lowest cost path.</returns>
        /// <param name="matrix">Cost matrix.</param>
        /// <param name="row">For specified row.</param>
        /// <param name="column">For specified column.</param>
        TraversalPath ComputeLowestCostPath(CostMatrix matrix, int row, int column)
        {
            TraversalPath lowestPath;

            if (column == 0)
            {
                //If we have reached the first column, we send back a new path instance
                lowestPath = new TraversalPath(matrix.NumberOfColumns);
            }
            else
            {
                //Calculate lowest path for one-row up from previous column
                var rowUpCostPath = ComputeLowestCostPath(matrix, matrix.RowUp(row), column - 1);
                //Calculate lowest path for current row from previous column
                var rowNextCostPath = ComputeLowestCostPath(matrix, row, column - 1);
                //Calculate lowest path for one-row down from previous column
                var rowDownCostPath = ComputeLowestCostPath(matrix, matrix.RowDown(row), column - 1);

                //and find the lowest path from all three possible moves
                lowestPath = rowUpCostPath;
                if (rowNextCostPath < lowestPath)
                {
                    lowestPath = rowNextCostPath;
                }
                if (rowDownCostPath < lowestPath)
                {
                    lowestPath = rowDownCostPath;
                }
            }

            //once we have the lowest possible move (or cost) we append that to current path
            //and also validate if it reaches max possible cost (if it does we invalidate the
            //path to abadon it)
            var nextPathTraversalCost = lowestPath.TotalCost + matrix[row, column];

            if (nextPathTraversalCost <= m_maxCost)
            {
                lowestPath.Append(row, matrix[row, column]);
            }
            else
            {
                lowestPath.Invalidate();
            }

            return(lowestPath);
        }
        /// <summary>
        /// Applies strategy/algorithm for calculating lowest-cost path across
        /// the specified cost-matrix.
        /// </summary>
        /// <returns>The lowest traversal path.</returns>
        /// <param name="matrix">The cost matrix.</param>
        public override TraversalPath GetLowestTraversalPath(CostMatrix matrix)
        {
            //start with null-path
            TraversalPath lowestCostPath = null;

            for (int row = 0; row < matrix.NumberOfRows; row++)
            {
                //for each row in matrix initiate recursive method to calculate lowest
                //traversal path. But, we start from the end (last column and move on to first column)
                var costPath = ComputeLowestCostPath(matrix, row, matrix.NumberOfColumns - 1);

                //for every row, compare cost (lowest traversal for corresponding row) and
                //accordingly set the lowestCostPath
                if (lowestCostPath == null || costPath <= lowestCostPath)
                {
                    lowestCostPath = costPath;
                }
            }

            //if not path found, send empty traversal path
            return(lowestCostPath ?? new TraversalPath(0));
        }
        /// <summary>
        /// Applies strategy/algorithm for calculating lowest-cost path across
        /// the specified cost-matrix.
        /// </summary>
        /// <returns>The lowest traversal path.</returns>
        /// <param name="matrix">The cost matrix.</param>
        public override TraversalPath GetLowestTraversalPath(CostMatrix matrix)
        {
            //create a matrix that will cache traversal-cost for each cell
            TraversalPath[,] cachedPaths = new TraversalPath[matrix.NumberOfRows, matrix.NumberOfColumns];

            //in this case we first go column by column
            for (int column = 0; column < matrix.NumberOfColumns; column++)
            {
                //and calculate lowest traversal cost for that particular cell (each row in column)
                for (int row = 0; row < matrix.NumberOfRows; row++)
                {
                    //initilize traversal path
                    cachedPaths[row, column] = new TraversalPath(column + 1);

                    //get cost for current cell
                    var currentCellCost = matrix[row, column];
                    int traversalCost;
                    if (column == 0)
                    {
                        //as it is first column, traversal-cost is same as current cell
                        traversalCost = currentCellCost;
                    }
                    else
                    {
                        //get adjacent up row index
                        var rowUpIndex = matrix.RowUp(row);
                        //get adjacent down row index
                        var rowDownIndex = matrix.RowDown(row);

                        //get traversal cost for adjacent up-row for previous column
                        var traversalPathFromUpRow = cachedPaths[rowUpIndex, column - 1];
                        //get traversal cost from current row for previous column
                        var traversalPathFromPrevRow = cachedPaths[row, column - 1];
                        //get traversal cost from adjacent down-row for previous column
                        var traversalPathFromDownRow = cachedPaths[rowDownIndex, column - 1];

                        //and find the lowest path from all three possible moves
                        var lowestTraversalPath = traversalPathFromUpRow;
                        if (traversalPathFromPrevRow < lowestTraversalPath)
                        {
                            lowestTraversalPath = traversalPathFromPrevRow;
                        }
                        if (traversalPathFromDownRow < lowestTraversalPath)
                        {
                            lowestTraversalPath = traversalPathFromDownRow;
                        }

                        //once we have the lowest traversal cost we copy that onto current cell cache
                        TraversalPath.Copy(lowestTraversalPath, cachedPaths[row, column]);
                        //and calculate total
                        traversalCost = lowestTraversalPath.TotalCost + currentCellCost;
                    }

                    //if traversal cost is valid, we append that current cell cache
                    if (traversalCost <= m_maxCost)
                    {
                        cachedPaths[row, column].Append(row, currentCellCost);
                    }
                    //else we abadon the path (that is invalidate the cell)
                    else
                    {
                        cachedPaths[row, column].Invalidate();
                    }
                }
            }

            //With the cache grid ready and initialized, we find the lowest cost by
            //traversing
            TraversalPath lowestCostPath = null;

            if (matrix.NumberOfColumns >= 1)
            {
                for (int row = 0; row < matrix.NumberOfRows; row++)
                {
                    var costPath = cachedPaths[row, matrix.NumberOfColumns - 1];
                    if (lowestCostPath == null || costPath <= lowestCostPath)
                    {
                        lowestCostPath = costPath;
                    }
                }
            }

            return(lowestCostPath ?? new TraversalPath(0));
        }