breadth-first search graph algorithm type #3. depth-first search

Post on 16-Dec-2015

231 Views

Category:

Documents

1 Downloads

Preview:

Click to see full reader

TRANSCRIPT

Breadth-First Search

Graph Algorithm Type #3

Depth-First Search

More Orderly Technique?

Breadth First Search (BFS)

int main () { Node *sourceNode = getNodebyID (sourceID); bool found = bfsPath (sourceNode, destID); . . . }

bool bfsPath (Node* sourceNode, int destID) { ...}

source

dest

start – 0 hops

1 hop away

2 hops away

3 hops away

Breadth First Searchbool bfsPath (Node* sourceNode, int destID) { list<Node *> wavefront; wavefront.push_back (sourceNode);

while (wavefront not empty) { Node *currNode = wavefront.front (); wavefront.pop_front(); // Remove node from wavefront

if (currNode->id == destID) return (true);

for each (outEdge of currNode) { Node *toNode = outEdge.toNode; wavefront.push_back (toNode); } } return (false); // No path exits!}

source

dest

0

1 2

3 4

5

wavefront = {0}

{1, 2}

{2, 3} {3,4,3}

{4,3,5}

{5}

wavefront = {}

{2}

{3} {4,3}

{3,5}{5,5} {5}

BFS: How Do I Print Out the Path?

source

dest

bool bfsPath (Node* sourceNode, int destID) { list<Node *> wavefront; wavefront.push_back (sourceNode);

while (wavefront not empty) { Node *currNode = wavefront.front (); wavefront.pop_front(); // Remove node from wavefront

if (currNode->id == destID) return (true);

for each (outEdge of currNode) { Node *toNode = outEdge.toNode; wavefront.push_back (toNode); } } return (false); // No path exits!}

0

1 2

3 4

5

wavefront = {0}

{1, 2}

{2, 3} {3,4,3}

{4,3,5}

{5}

wavefront = {}

{2}

{3} {4,3}

{3,5}What do I know here?{5,5} {5}

BFS: How Do I Print Out the Path?Need more information!

struct waveElem { Node *node; int edgeID; // ID of edge used to reach this node waveElem (Node *n, int id) {node = n; edgeID = id;}};

#define NO_EDGE -1 // Illegal edge ID no edge

Why did I use an int instead of an Edge?

BFS: How Do I Print Out the Path?

source

dest

bool bfsPath (Node* sourceNode, int destID) { list<waveElem> wavefront; wavefront.push_back (waveElem (sourceNode, NO_EDGE));

while (wavefront not empty) { waveElem curr = wavefront.front (); wavefront.pop_front(); // Remove node from wavefront

if (curr.node->id == destID) return (true);

for each (outEdge of curr.node) { Node *toNode = outEdge.toNode; wavefront.push_back ( waveElem(toNode, outEdge.id); } } return (false); // No path exits!}

0

1 2

3 4

5

{4/c,5/f}

f

c

{5/f}Know I got here from edge f. Good enough?

ab

de

BFS: How Do I Print Out the Path?bool bfsPath (Node* sourceNode, int destID) { list<waveElem> wavefront; wavefront.push_back (waveElem (sourceNode, NO_EDGE));

while (wavefront not empty) { waveElem curr = wavefront.front (); wavefront.pop_front(); // Remove node from wavefront curr.node->reachingEdge = curr.edgeID;

if (curr.node->id == destID) return (true);

for each (outEdge of curr.node) { Node *toNode = outEdge.toNode; wavefront.push_back ( waveElem(toNode, outEdge.id); } } return (false); // No path exits!}

source

dest

f

c

a b

de

NO_EDGE

a b

e c

f

d

BFS: How Do I Print Out the Path?int main () { Node *sourceNode = getNodebyID (sourceID); bool found = bfsPath (sourceNode, destID); if (found) list<Edge> path = bfsTraceBack (destID);}

list<Edge> bfsTraceBack (int destID) { list<Edge> path; Node *currNode = getNodebyID (destID); prevEdge = currNode->reachingEdge;

while (prevEdge != NO_EDGE) { path.push_front (prevEdge); currNode = prevEdge.fromNode; prevEdge = currNode->reachingEdge; } return (path);}

source

dest

f

c

a b

de

NO_EDGE

a b

c

f

d

path = {}path = {f}path = {f,d}path = {f,d,b}

reachingEdge = areachingEdge = c

Min. Path Issues

source

dest

c

a

b

d

wavefront =

0

1

2

3

{0}{1,2}{2,3}{3,1}

4

{1,4}{4,3}

b

d

e

e

What happened?• Node 1 was re-expanded• Overwrote the reachingEdge• Messed up the path traceback

d

source

reachingEdge = a

Solution?

dest

c

a

b

d

wavefront =

0

1

2

3

{0}{1,2}{2,3}{3,1}

4

{1,4}{4}

b

e

e

• Mark nodes as visited when you reach them

• Never allow them to be visited again

d

source

reachingEdge = a

Solution?

dest

c

a

b

d

wavefront =

0

1

2

3

{0}{1,2}{2,3}{3,1}

4

{1,4}{4}

b

e

e

• Another test case• With travel times

t = 5 s

t = 5 s

t = 20 s

e

d

source

reachingEdge = a

Visited Flag: Problem

dest

c

a

b

d

0

1

2

3

4

b

e

t = 5 s

t = 5 s

t = 20 s

Shortest path

Path we obtain

a, 20 sc, 10 s

Solution #2

source

dest

c

a

b

d

wavefront =

0

1

2

3

{0}{1,2}{2,3}{3,1}

4

{1,4}{4,3}

b, 5 s

d, 26 s

e, 29 s

e

1. Store shortest travel time from source at each node

2. Only process node if shortest travel time to it has dropped

t = 5 s

t = 5 s

t = 20 s

t = 6 s

t = 3 s

Half fixed. Got right path, but wrong travel time at dest!

a, 20 s

Solution #2

source

dest

c

a

b

d

wavefront =

0

1

2

3

{0}{1,2}{2,3}{3,1}

b, 5 s

d, 26 s

Another Test Case

t = 5 s

t = 5 s

t = 20 s

t = 6 s

This path is wrong!

a, 20 sc, 10 s

Solution #2++

source

dest

c

a

b

d

wavefront =0

1

2

3

{0/0s}{1/20s,2/5s}{2/5s,3/26s}{3/26s,1/10s}

4

{1/10s,4/29s}{4/29s,3/16s}

b, 5 s

d, 26 s

e, 29 s

e

1. Store shortest travel time from source at each node

2. Only update reachingEdge if shortest travel time drops

3. Don’t stop BFS on first reach of destination• Continue BFS until all

entries in wavefront have higher travel time than best path found so far

t = 5 s

t = 5 s

t = 20 s

t = 6 s

t = 3 s

d, 16 s

e, 19 s

{3/16s}{4/19s}

top related