tree graph - find how many pairs of vertices, for which the sum of edges on a path between them is C - algorithm

I've got a weighted tree graph, where all the weights are positive. I need an algorithm to solve the following problem.
How many pairs of vertices are there in this graph, for which the sum of the weights of edges between them equals C?
I thought of a solutions thats O(n^2)
For each vertex we start a DFS from it and stop it when the sum gets bigger than C. Since the number of edges is n-1, that gives us obviously an O(n^2) solution.
But can we do better?

For an undirected graph, in terms of theoretic asymptotic complexity - no, you cannot do better, since the number of such pairs could be itself O(n^2).
As an example, take a 'sun/flower' graph:
G=(V[union]{x},E)
E = { (x,v) | v in V }
w(e) = 1 (for all edges)
It is easy to see that the graph is indeed a tree.
However, the number of pairs that have distance of exactly 2 is (n-1)(n-2) which is in Omega(n^2), and thus any algorithm that finds all of them will be Omega(n^2) in this case.

Related

How to Find shortest paths with k negative weighted edges?

The problem is to find shortest paths from a start vertice to all other vertices in a directed graph.
But the graph will have m positive weighted edges and k negative weighted edges, and it's guaranteed that negative weighted edges will be not in a cycle. In other words, there is no negative weighted cycle in this graph.
I tried to directly use Bellman-Ford and SPFA to solve this question but does there exists a faster way to do this?
If k is large enough, you should probably just run Bellman–Ford and call it a day.
If k is small, you can borrow the re-weighting trick from Johnson’s algorithm, but with a faster initialization than just running Bellman–Ford. Recall that Johnson computes a potential π(v) for each vertex and adjusts the cost of each arc vw from c(vw) to c′(vw) = c(vw) − π(v) + π(w), choosing π so that c′ is nowhere negative. The shortest path between s and t is the same with respect to c as with respect to c′,
Suppose that the input graph G has exactly one negative arc, let’s say c(xy) < 0. Use Dijkstra’s algorithm to compute distances in G − xy from y to all other vertices. Then define π(v) = distance(y, v). The correctness proof follows the proof of Johnson’s algorithm; the arc xy can’t be part of a shortest path from y because there are no negative cycles, so Dijkstra on G - xy in fact computes a shortest path tree for G.
For general k, we can do this recursively. If k = 0, run Dijkstra. Otherwise, remove a negative arc and compute shortest paths recursively instead of with Dijkstra. Once we have good values for π, run Dijkstra one more time, from the given start vertex.
The overall running time is O((k + 1) (m + n log n)) with Fibonacci heaps.

Describing an algorithm at most O(nm log n) run time

If I had to give an algorithm in O|V|3| that takes as input a directed graph with positive edge lengths and returns the length of the shortest cycle in the graph (if the graph is acyclic, it should say so). I know that it will be:
Let G be a graph, define a matrix Dij which stores the shortest path from vertex i to j for any pair of vertices u,v. There can be two shortest paths between u and v. The length of the cycle is Duv+ Dvu. This then is enough to compote the minimum of the Duv+Dvu for any given pair of vertices u and v.
Could I write this in a way to make it at most O(nm log n) (where n is the number of vertices and m is the number of edges) instead of O|V|3|?
Yes, in fact this problem can be solved in O(nm) according to a conference paper by Orlin and Sedeño-Noda (2017), titled An O(nm) time algorithm for finding the min length directed cycle in a graph:
In this paper, we introduce an O(nm) time algorithm to determine the minimum length directed cycle (also called the "minimum weight directed cycle") in a directed network with n nodes and m arcs and with no negative length directed cycles.

Special Case for MST algorithm in linear time

Let G = (V, E) be a weighted undirected connected graph, where all the
edge weights are distinct. Let T denote the minimum spanning tree.
Suppose that G has m ≤ n + 157 edges. For this special case, give an MST
algorithm that runs in O(n) time beating Kruskals and Prims algorithm.
Any hints?
First verify that the graph is connected.
Then repeat until the graph is a tree (# edges = n-1):
Find a cycle using DFS. There must be one since #edges >= n
Remove the longest edge in the cycle. It cannot be part of the MST.
When done you are left with the MST.
Even though this can take O(n) time per iteration, there will be at most 158 iterations, so that is still O(n) all together.

Design an algorithm which finds a minimum spanning tree of this graph in linear time

I am working on a problem in which I am given an undirected graph G on n vertices and with m edges, such that each edge e has a weight w(e) ∈ {1, 2, 3}. The task is to design an algorithm which finds a minimum spanning tree of G in linear time (O(n + m)).
These are my thoughts so far:
In the Algorithmic Graph Theory course which I am currently studying, we have covered Kruskal's and Prim's MST Algorithms. Perhaps I can modify these in some way, in order to gain linear time.
Sorting of edges generally takes log-linear (O(mlog(m))) time; however, since all edge weights are either 1, 2 or 3, Bucket Sort can be used to sort the edges in time linear in the number of edges (O(m)).
I am using the following version of Kruskal's algorithm:
Kruskal(G)
for each vertex 𝑣 ∈ 𝑉 do MAKE−SET(𝑣)
sort all edges in non-decreasing order
for edge 𝑢, 𝑣 ∈ 𝐸 (in the non-decreasing order) do
if FIND 𝑢 ≠ FIND(𝑣) then
colour (𝑢, 𝑣) blue
UNION(𝑢, 𝑣)
od
return the tree formed by blue edges
Also, MAKE-SET(x), UNION(x, y) and FIND(x) are defined as follows:
MAKE-SET(𝒙)
Create a new tree rooted at 𝑥
PARENT(𝑥)=x
UNION(𝒙, 𝒚)
PARENT FIND(𝑥) ≔ 𝐹𝐼𝑁𝐷(𝑦)
FIND(𝒙)
𝑦 ≔ 𝑥
while 𝑦 ≠ PARENT(𝑦) do
𝑦 ≔ PARENT(𝑦)
return y
The issue I have at the moment is that, although I can implement the first two lines of Kruskal's in linear time, I have not managed to do the same for the next four lines of the algorithm (from 'for edge u, ...' until 'UNION (u, v)').
I would appreciate hints as to how to implement the rest of the algorithm in linear time, or how to find a modification of Kruskal's (or some other minimum spanning tree algorithm) in linear time.
Thank you.
If you use the Disjoint Sets data structure with both path compression and union by rank, you get a data structure whose each operation's complexity grows extremely slowly - it is something like the inverse of the Ackermann function, and is not that large for sizes such as the estimated number of atoms in the universe. Effectively, then, each operation is considered constant time, and so the rest of the algorithm is considered linear time as well.
From the same wikipedia article
Since α(n) is the inverse of this function, α(n) is less than 5 for all remotely practical values of n. Thus, the amortized running time per operation is effectively a small constant.

Breadth-first search algorithm (graph represented by the adjacency list) has a quadratic time complexity?

A friend told me that breadth-first search algorithm (graph represented by the adjacency list) has a quadratic time complexity. But in all the sources says that the complexity of BFS algortim exactly O (|V| + |E|) or O (n + m), from which we obtain a quadratic complexity ?
All the sources are right :-) With BFS you visit each vertex and each edge exactly once, resulting in linear complexity. Now, if it's a completely connected graph, i.e. each pair of vertices is connected by an edge, then the number of edges grows quadratic with the number of vertices:
|E| = |V| * (|V|-1) / 2
Then one might say the complexity of BFS is quadratic in the number of vertices: O(|V|+|E|) = O(|V|^2)
BFS is O(E+V) hence in terms of input given it is linear time algorithm but if vertices of graph are considered then no of edges can be O(|V|^2) in dense graphs hence if we consider time complexity in terms of vertices in graph then BFS is O(|V|^2) hence can be considered quadratic in terms of vertices
O(n + m) is linear in complexity and not quadratic. O(n*m) is quadratic.
0. Initially all the vertices are labelled as unvisited. We start from a given vertex as the current vertex.
1. A BFS will cover (visit) all the adjacent unvisited vertices to the current vertex queuing up these children.
2. It would then label the current vertex as 'visited' so that it might not be visited (queued again).
3 BFS would then take out the first vertex from the queue and would repeat the steps from 1 till no more unvisited vertices remain.
The runtime for the above algorithm is linear in the total no. of vertices and edges together because the algorithm would visit each vertex once and check each of its edges once and thus it would take no. of vertices + no. of edges steps to completely search the graph

Resources