I was given a graph, including a start vertex, other vertices, and edges represent the costs going from one vertex to another. I need to find the set of destination vertices that I can travel to from the start vertex. The budget is a certain amount of dollars and the travel total cost should be within the budget. How can i implement the Dijkstra's algorithm to this problem? I think we usually use Dijkstra to find the shortest path between two fixed vertices before. But I am not sure how to implement Dijkstra on this budget problem. If someone can give some ideas, that really helps!
To my undersatanding, Dijkstra's algorithm solves the single-source shortest path problem. This means that the resulting data structure is a tree rooted at the starting node. Typically, an implementation would store the minimum cost to reach each node from the starting node. In total, the set of vertices that can be reached within the budget are the ones to which the cost of the shortest path does not exceed the budget. The algorithm itself does not need to be modified; in an additional step, the nodes which can be reached within budged has to be returned as the output.
If you use Dijkstra algorithm, you may end up with the below scenarios:
Assuming budget of 50 and the graph of 4 nodes (start, node 1, node 2, node 3)
Start Node -> node 1 (15) -> node 2 (10): so total cost is 25
Start Node -> node 3 (15): total cost is 15
So now what is your expected result? You should go to node 1 then node 2 and ignore node 3 (since you cannot return back to start then go to node 3, the return will cost 30 too). Or you should go to node 1, back to start, then go to node 3 (total cost of 45, the largest cost you can utilise)
What you need is not the shortest path covering all destinations which is Floyd-Warshall algorithm https://en.wikipedia.org/wiki/Floyd–Warshall_algorithm
Related
This is for a homework problem -
I need to find the median of a Binary Search Tree in O(h) time - meaning, I cant go through the whole tree to find it. I need to find the median by going through the left or right side of the tree, in a recursion solution.
I've placed an index into each node of the BST, using inorder traversal.
So if a BST has 99 nodes, the smallest node has an index of 1, the next smallest has index of 2 etc etc...while the largest node has index of 99. THis indexing is also required of the assignment.
So whichever side is heavier, has the median.
So here's what I was thinking:
if the left side has more nodes median is on the left. if right side has more nodes, median is on the right. if the left and right sides have equal num of nodes, median is the main root of the whole tree.
But I can't think of how the nodes' indexes would play a role in any of this. I was thinking of using the difference of 2 nodes' indexes to see if 1 side is heavier, but this would require me to go through the whole tree I think, so this would be O(n).
Please set me on a clearer path or a hint or 2.
I need a JAVA code that could help me find the height of the Minimum spanning tree.
Basically i m looking for an extension of the
Prim's/Kruskal's algo that not only gives the height of the MST but also gives its height.
Thanks in advance.
Take as the root vertex one of the tree's centers and calculate the maximal distance from the chosen center to the leaf nodes.
The height can the be calculated in the following way:
set the height to 0
while there are at least 3 remaining vertices:
delete all leaf vertices
height := height+1
if 2 vertices remain:
height := height+1
the remaining vertices are the centers of the tree.
The time complexity is O(n).
A practical way of calculating the height would be to combine all leaf nodes int a single node that serves as a root, then calculate the MST of that modification and the height as the maximum distance from generated root node to the newly generated leaf nodes.
I am not writing the code here, just giving you a hint.
In every node keep a variable that stores the height/depth of that node.
So, depth for starting node will be 0. Now, whenever you add a edge to the MST, increase the depth of the new node by 1.
Currently you have the following discovered nodes with the following depth.
a 0
b 1
c 1Now suppose you want to add the edge from c to d, so the depth of node d will be depth(c)+1, i.e 1+1=2.
Also, you can keep a track of the maximum depth among all nodes at each step of the algorithm.
So, finally answer will be the maximum depth among all the nodes of the tree.
Take this node weighted graph for example :
The maximum subgraph containing exactly 1 node (and the 'entry point') would be 14.
The maximum subgraph containing exactly 2 nodes (and the 'entry point') would be 14 / 9.
The maximum subgraph containing exactly 3 nodes (and the 'entry point') would be 3 / 19 / 15.
The maximum subgraph containing exactly 4 nodes (and the 'entry point') would be 14 / 1 / 7 / 240.
I can't manage to think of a better method than a bruteforce to get the maximum subgraph.
And if there is no known efficient algorithm, would a genetic algorithm be find in that case (the crossovers seem tricky) ?
I think you can modify Dijkstra's algorithm to solve this problem.
With Dijkrasta's algorithm you are solving the shortest path. Just change that to find the maximum path. To restrict it to only 1,2,3 nodes in a graph, keep track of the number of nodes it takes to get to each node when you "visit it". Stop when there are no other nodes with a count less than the number of nodes you are looking for.
I have an undirected graph A that has : no multiple-links between any two nodes , no self-connected node, there can be some isolated nodes (nodes with degree 0).
I need to go through all the possible combinations of pair of nodes in graph A to assign some kind of score for non-existence links (Let say if my graph has k nodes and n links, then the number of combination should be (k*(k-1)/2 - n) of combinations). The way that I assign score is based on the common neighbor nodes between the 2 nodes of combination.
Ex: score between A-D should be 1, score between G-D should be 0 ...
The biggest problem is that my graph has more than 100.000 nodes and it was too slow to handle almost 10^10 combinations which is my first attempt to approach the solution.
My second thought is since the algorithm is based on common neighbors of the node, I might only need to look at the neighbors so that I can assign score which is different from 0. The rest can be determined as 0 and no need to compute. But this could possibly repeat a combination.
Any idea to approach this solution is appreciated. Please keep in mind that the actual network has more than 100.000 nodes.
If you represent your graph as an adjacency list (rather than an adjacency matrix), you can make use of the fact that your graph has only 600,000 edges to hopefully reduce the computation time.
Let's take a node V[j] with neighbors V[i] and V[k]:
V[i] ---- V[j] ---- V[k]
To find all such pairs of neighbors you can take the list of nodes adjacent to V[j] and find all combinations of those nodes. To avoid duplicates you will have to generate the combinations rather than the permutations of the end nodes V[i] and V[k] by requiring that i < k.
Alternatively, you can start with node V[i] and find all of the nodes that have a distance of 2 from V[i]. Let S be the set of all the nodes adjacent to V[i]. For each node V[j] in S, create a path V[i]-V[j]-V[k] where:
V[k] is adjacent to V[j]
V[k] is not an element of S (to avoid directly connected nodes)
k != i (to avoid cycles)
k > i (to avoid duplications)
I personally like this approach better because it completes the adjacency list for one node before moving on to the next.
Given that you have ~600,000 edges in a graph with ~100,000 nodes, assuming an even distribution of edges across all of the nodes each node would have an average degree of 12. The number of possible paths for each node is then on the order of 102. Over 105 nodes that gives on the order of 107 total paths rather than the theoretical limit of 1010 for a complete graph. Still a large number, but a thousand times faster than before.
How to decide heuristic cost for the cities connected with roads problem. The graph has non negative weighted unidirectional edges and no edge connects any vertex to itself. In this graph, there is only one edge between any two vertices. My aim is to get the shortest distance between single source and single destination.
If your edges lie in a Euclidian plane, your vertices correspond to roads, and the vertex cost is the length of the road, then the Euclidian distance or L2 norm is a good choice for the heuristic cost.
Here's why. But first, some quick terminology:
Let f(x) be the path cost, the calculated shortest distance from the start node to node x.
Let h(x) be the heuristic cost, an estimate of the distance to the goal from node x.
Because A* is a directed best-first search algorithm. At each step it moves to the node which minimizes h(x) + f(x) (and calculating h(x) requires that we have a goal node in mind).
For this approach to be guaranteed to find the correct shortest patch distance between the start and end nodes, h(x) must be an admissible heuristic. This essentially means that it must not overestimate the distance to the goal node.
Therefore, if your nodes are organized on a Euclidian plane, and your costs correspond to the L2 norm distance between the nodes, then the Euclidian distance or L2 norm between the current node x and the goal node is guaranteed to be an admissible heuristic (it's the shortest possible path between the two nodes, so any actual path along a series of vertices in your graph must be longer).
As a bonus, it's informative to note that Dijkstra's Algorithm is simply a special case of A* with h(x) = 0. For any node, we assume that the path to the goal is 0, which means we simply take the smallest possible step. This is certainly an admissible heuristic because the distance between any two nodes cannot be less than 0 (if we're assuming non-negative edge costs).
If you're trying to optimize for distance travelled, euclidean distance is a good baseline heuristic.
If you're given a weighted graph, use the edge weight as if it's the length of the segment. The shortest path in a weighted graph is the path with the lowest combined edge weight.