# The implementation of the shortest path finding algorithm (dixstra algorithm) in php

Keywords: Python PHP

Refer to Chapter 7 of algorithm diagram for details. The original book was written in python, and I wrote it again in PHP, which was slightly improved

Test these three exercises in the book

I found another "difficult" question on the Internet

Upper Code:

```class ShortPath{
protected \$graph=[];//A graph can be represented only by storing the neighbors corresponding to each node

protected \$parents=[];//Save the parent relationship, and finally backtrack the shortest path through this array

protected \$costs;//Cost from start to each node

protected \$infinity=999999;//Use a large number to represent a positive infinity

protected \$processed=[];//key of processed node

public function __construct(\$graph)
{
\$this->graph=\$graph;

//Initialize the parent array, that is, only the neighbors of start are known, that is, the parent of start
foreach (\$this->graph['start'] as \$k=>\$v) {
\$this->parents[\$k]='start';
}

//Initialize the cost array, that is, only the cost of the neighbor node of start is known, and all other nodes are positive infinite
foreach (\$this->graph as \$k=>\$v) {
if(\$k=='start'){
\$this->costs=\$this->graph['start'];
}elseif(empty(\$this->costs[\$k])){
\$this->costs[\$k]=\$this->infinity;
}
}
\$this->costs['finish']=\$this->infinity;
}

public function find(){
\$nodeKey=\$this->findLowestCostNode(\$this->costs);
while (\$nodeKey){//As long as there are unprocessed nodes
\$cost=\$this->costs[\$nodeKey];
\$neighbors=\$this->graph[\$nodeKey] ?? [];//Take neighbors
//Traversing neighbors
foreach (\$neighbors as \$k=> \$v) {
\$newCost=\$cost+\$v;
if(\$this->costs[\$k] > \$newCost){
\$this->parents[\$k]=\$nodeKey;
}
}

//Debug output
echo 'Current node:' .\$nodeKey . PHP_EOL;
echo 'Neighbours:' . PHP_EOL;
print_r(\$neighbors);
echo 'Expenses:' . PHP_EOL;
print_r(\$this->costs);

//Now that all neighbors of the node have been processed, mark the node as processed
\$this->processed[]=\$nodeKey;
//Find the next node to be processed
\$nodeKey=\$this->findLowestCostNode();
}
\$this->showResult();
}

//Find the shortest one among the unprocessed nodes
protected function findLowestCostNode(){
\$lowestCost=\$this->infinity;//Set positive infinity here so that when you first enter the loop, it must be larger than the first element
\$lowestCostKey=false;//The key of the shortest path node to return
foreach (\$this->costs as \$k=>\$v) {
if(\$v<\$lowestCost && !in_array(\$k,\$this->processed)){
\$lowestCost=\$v;
\$lowestCostKey=\$k;
}
}
return \$lowestCostKey;
}

//Beautify display processing results
protected function showResult(){
\$path=[];
\$key='finish';
//From the end, find the parent and trace back the shortest route
while (isset(\$this->parents[\$key])){
array_unshift(\$path,\$key);
\$key=\$this->parents[\$key];
}
echo 'The shortest path length is:' . \$this->costs['finish'] . PHP_EOL;
echo 'The route is:start->' . implode('->',\$path) . PHP_EOL;
}

}

//Corresponding exercise A
\$graph1=[
"start"=>[
"a"=>2,
"b"=>5,
],
"a"=>[
"b"=>8,
"d"=>7,
],
"b"=>[
"c"=>4,
"d"=>2,
],
"c"=>[
"finish"=>3,
"d"=>6
],
"d"=>[
"finish"=>1
]
];

//Corresponding Exercise B
\$graph2=[
"start"=>[
"a"=>10,
],
"a"=>[
"c"=>20,
],
"b"=>[
"a"=>1,
],
"c"=>[
"b"=>1,
"finish"=>30,
],
];

//Corresponding exercise C. It can be seen that the algorithm is not suitable for the case with negative weight edges
\$graph3=[
"start"=>[
"a"=>2,
"b"=>2,
],
"a"=>[
"c"=>2,
"finish"=>2
],
"b"=>[
"a"=>2,
],
"c"=>[
"b"=>-100,
"finish"=>2,
],
];

//Corresponding to the last question, change v0 in the figure to start and v8 to finish
\$graph4=[
"start"=>[
"v1"=>1,
"v2"=>5,
],
"v1"=>[
"start"=>1,
"v2"=>3,
"v3"=>7,
"v4"=>5,
],
"v2"=>[
"start"=>5,
"v1"=>3,
"v4"=>1,
],
"v3"=>[
"v1"=>7,
"v2"=>2,
"v6"=>3,
],
"v4"=>[
"v1"=>5,
"v2"=>1,
"v3"=>2,
"v5"=>3,
"v6"=>6,
"v7"=>9,
],
"v5"=>[
"v2"=>6,
"v4"=>3,
"v7"=>5,
],
"v6"=>[
"v3"=>3,
"v4"=>6,
"v7"=>2,
"finish"=>7
],
"v7"=>[
"v4"=>9,
"v5"=>5,
"v6"=>2,
"finish"=>4
],
];

\$obj=new ShortPath(\$graph4);
\$obj->find();

```

Output of the last question