60class EdgeWeightedGraph;
63#define OGDF_STEINERTREE_RZLOSS_REDUCE_ON
101 if (
m_alg ==
nullptr) {
104 return m_alg->numberOfGeneratedComponents();
109 if (
m_alg ==
nullptr) {
112 return m_alg->numberOfContractedComponents();
117 if (
m_alg ==
nullptr) {
120 return m_alg->numberOfComponentLookUps();
135 return m_alg->getApproximation(finalSteinerTree);
141 template<
typename TYPE>
161 template<
typename FCG>
177 tree.setOriginalGraph(m_G);
181 m_G.numberOfEdges())) {
184 findFullComponentsEMV(
tree);
192 generateInitialTerminalSpanningTree(
tree, distance, pred);
196 findFullComponentsDW(
tree, distance, pred);
198 findFull3Components(
tree, distance, pred);
202 m_fullCompStore.computeAllLosses();
203 m_componentsGenerated = m_fullCompStore.size();
226 template<
typename TERMINAL_CONTAINER>
240 std::unique_ptr<steiner_tree::SaveStatic<T>>
m_save;
272 , m_isTerminal(isTerminal)
273 , m_terminals(terminals)
275 m_restricted(min(restricted, terminals.size()))
276 , m_fullCompStore(m_G, m_terminals, m_isTerminal)
277 , m_isNewTerminal(m_G, false)
278 , m_componentsGenerated(0)
279 , m_componentsContracted(0)
280 , m_componentsLookUps(0) {
283 for (
node v : terminals) {
303 for (
node v : m_terminals) {
312 if (p[vO] !=
nullptr) {
313 steinerTree.
newEdge(u, v, dist[vO]);
326 fcg.
call(m_G, m_terminals, m_isTerminal, distance, pred,
332 minComp.
newEdge(minComp.
newNode(t0), minCenterC, distance[t0][minCenter]);
333 minComp.
newEdge(minComp.
newNode(t1), minCenterC, distance[t1][minCenter]);
334 minComp.
newEdge(minComp.
newNode(t2), minCenterC, distance[t2][minCenter]);
336#ifdef OGDF_STEINERTREE_RZLOSS_REDUCE_ON
337 if (gain(std::vector<node> {t0, t1, t2},
tree) > minCost) {
338 m_fullCompStore.insert(minComp);
341 m_fullCompStore.insert(minComp);
347template<
typename FCG>
354 terminalSubset.
list(terminals);
355#ifdef OGDF_STEINERTREE_RZLOSS_REDUCE_ON
358 fcg.getSteinerTreeFor(terminals, component);
361 gain(terminals,
tree) > cost &&
363 fcg.isValidComponent(component)) {
364 m_fullCompStore.insert(component);
375 retrieveComponents(fcg,
tree);
383 retrieveComponents(fcg,
tree);
388 while (!m_fullCompStore.isEmpty()) {
390 double r = extractMaxComponent(steinerTree, maxCompId);
392 ++m_componentsContracted;
395 m_fullCompStore.foreachNode(maxCompId, [&](
node v) { m_isNewTerminal[v] =
true; });
397 contractLoss(steinerTree, maxCompId);
398 m_fullCompStore.remove(maxCompId);
400 if (!m_fullCompStore.isEmpty()) {
414 for (
int i = 0; i < m_fullCompStore.size();) {
415 ++m_componentsLookUps;
416 const double winAbs =
417 gain(m_fullCompStore.terminals(i), steinerTree) - m_fullCompStore.cost(i);
419 const double r = winAbs / m_fullCompStore.loss(i);
426#ifdef OGDF_STEINERTREE_RZLOSS_REDUCE_ON
429 m_fullCompStore.remove(i);
437template<
typename TERMINAL_CONTAINER>
440 std::set<edge> saveEdges;
444 for (
auto it1 = terminals.begin(); it1 != terminals.end(); ++it1) {
447 for (
auto it2 = next; it2 != terminals.end(); ++it2) {
448 const edge e = m_save->saveEdge(*it1, *it2);
453 for (
edge e : saveEdges) {
454 result += steinerTree.
weight(e);
465 for (
edge e : m_fullCompStore.lossBridges(compId)) {
466 const node u = m_fullCompStore.lossTerminal(e->source());
468 const node v = m_fullCompStore.lossTerminal(e->target());
471 m_fullCompStore.graph().weight(e));
Extends the GraphCopy concept to weighted graphs.
Definition of ogdf::steiner_tree::Full3ComponentGeneratorVoronoi class template.
Definition of the FullComponentDecisions class.
Definition of the FullComponentGeneratorCaller class template.
Definition of the ogdf::steiner_tree::FullComponentGeneratorDreyfusWagner class template.
Definition of the ogdf::steiner_tree::FullComponentGeneratorDreyfusWagnerWithoutMatrix class template...
Definition of the FullComponentStore class template.
Includes declaration of graph class.
Declaration of doubly linked lists and iterators.
Implementation of Mehlhorn's minimum Steiner tree 2(1-1/l)-approximation algorithm.
Declaration of ogdf::MinSteinerTreeModule.
#define OGDF_STEINERTREE_RZLOSS_REDUCE_ON
Implementation of the staticLCATree option for calculating save edges in Zelikovsky's 11/6-approximat...
A class that allows to enumerate k-subsets.
Basic declarations, included by all source files.
Class for the representation of edges.
edge newEdge(node u, node v, T weight)
void setOriginalGraph(const Graph *wG) override
Re-initializes the copy using G (which might be null), but does not create any nodes or edges.
const EdgeArray< T > & edgeWeights() const
T weight(const edge e) const
node newNode(node vOrig)
Creates a new node in the graph copy with original node vOrig.
const Graph & original() const
Returns a reference to the original graph.
edge copy(edge e) const override
Returns the first edge in the list of edges corresponding to edge e.
int numberOfNodes() const
Returns the number of nodes in the graph.
int numberOfEdges() const
Returns the number of edges in the graph.
internal::GraphObjectContainer< NodeElement > nodes
The container containing all node objects.
Doubly linked lists (maintaining the length of the list).
Serves as an interface for various methods to compute or approximate minimum Steiner trees on undirec...
static void sortTerminals(List< node > &terminals)
Sort terminals by index.
double extractMaxComponent(const EdgeWeightedGraphCopy< T > &steinerTree, int &maxCompId)
Traverses over all full components and finds the one with the highest win-objective.
std::unique_ptr< steiner_tree::SaveStatic< T > > m_save
The save data structure.
const EdgeWeightedGraph< T > & m_G
The original edge-weighted graph.
NodeArray< bool > m_isNewTerminal
Incidence vector for nonterminal nodes marked as terminals for improvement.
Main(const EdgeWeightedGraph< T > &G, const List< node > &terminals, const NodeArray< bool > &isTerminal, int restricted)
long m_componentsGenerated
Number of generated components.
long m_componentsContracted
Number of contracted components.
long numberOfContractedComponents()
Returns the number of contracted components.
const NodeArray< bool > & m_isTerminal
Incidence vector for terminal nodes.
void findFullComponentsEMV(const EdgeWeightedGraphCopy< T > &tree)
Find full components using algorithm by Erickson et al.
void retrieveComponents(const FCG &fcg, const EdgeWeightedGraphCopy< T > &tree)
Auxiliary function to retrieve components by Dreyfus-Wagner/Erickson et al implementation.
long numberOfComponentLookUps()
Returns the number of components lookups during execution time.
T gain(const TERMINAL_CONTAINER &terminals, const EdgeWeightedGraphCopy< T > &steinerTree)
void generateInitialTerminalSpanningTree(EdgeWeightedGraphCopy< T > &steinerTree, const NodeArray< NodeArray< T > > &distance, const NodeArray< NodeArray< edge > > &pred)
Builds a minimum terminal spanning tree (via a MST call on the complete terminal graph)
long numberOfGeneratedComponents()
Returns the number of generated components.
void findFullComponentsDW(const EdgeWeightedGraphCopy< T > &tree, const NodeArray< NodeArray< T > > &distance, const NodeArray< NodeArray< edge > > &pred)
Find full components using algorithm by Dreyfus-Wagner.
steiner_tree::FullComponentWithLossStore< T > m_fullCompStore
All generated full components.
long m_componentsLookUps
Number of components lookups.
void findFull3Components(const EdgeWeightedGraphCopy< T > &tree, const NodeArray< NodeArray< T > > &distance, const NodeArray< NodeArray< edge > > &pred)
Find full components of size 3.
void multiPass(EdgeWeightedGraphCopy< T > &steinerTree)
Contraction phase of the algorithm.
List< node > m_terminals
List of terminal nodes (will be copied and sorted)
void contractLoss(EdgeWeightedGraphCopy< T > &steinerTree, int compId)
Contracts the loss of a full component and integrates it into the given terminal-spanning tree.
void setup(EdgeWeightedGraphCopy< T > &tree)
Setup (build initial terminal-spanning tree, its save data structure, and find all components)
T getApproximation(EdgeWeightedGraphCopy< T > *&finalSteinerTree) const
int m_restricted
Parameter for the number of terminals in a full component.
This class implements the loss-contracting (1.55+epsilon)-approximation algorithm for the Steiner tre...
long numberOfComponentLookUps()
Returns the number of components lookups during execution time.
virtual T computeSteinerTree(const EdgeWeightedGraph< T > &G, const List< node > &terminals, const NodeArray< bool > &isTerminal, EdgeWeightedGraphCopy< T > *&finalSteinerTree) override
Builds a minimum Steiner tree given a weighted graph and a list of terminals.
long numberOfContractedComponents()
Returns the number of contracted components.
long numberOfGeneratedComponents()
Returns the number of generated components.
MinSteinerTreeRZLoss(int v)
virtual ~MinSteinerTreeRZLoss()
void setMaxComponentSize(int k)
Sets the maximal number of terminals in a full component.
std::unique_ptr< Main > m_alg
Class for the representation of nodes.
node succ() const
Returns the successor in the list of all nodes.
Enumerator for k-subsets of a given type.
void begin(int low, int high)
Initializes the SubsetEnumerator to enumerate subsets of cardinalities from low to high.
bool valid() const
Checks if the current subset is valid. If not, the subset is either not initialized or all subsets ha...
void list(List< T > &subset) const
Obtains (appends) a list of the subset members.
void next()
Obtains the next subset if possible. The result should be checked using the valid() method.
RegisteredArray for nodes, edges and adjEntries of a graph.
Full 3-component generation using Voronoi regions.
void call(const EdgeWeightedGraph< T > &G, const List< node > &terminals, const NodeArray< bool > &isTerminal, const NodeArray< NodeArray< T > > &distance, const NodeArray< NodeArray< edge > > &pred, std::function< void(node, node, node, node, T)> generateFunction) const
Generate full components and call generateFunction for each full component.
static void computeDistanceMatrix(NodeArray< NodeArray< T > > &distance, NodeArray< NodeArray< edge > > &pred, const EdgeWeightedGraph< T > &graph, const List< node > &terminals, const NodeArray< bool > &isTerminal, int restricted)
Computes distance and predecessor matrix.
A generator for restricted full components (for Steiner tree approximations) based on the Dreyfus-Wag...
void call(int restricted)
A generator for restricted full components (for Steiner tree approximations) based on the Dreyfus-Wag...
void call(int restricted)
A data structure to store full components with additional "loss" functionality.
This class behaves basically the same as SaveDynamic except that the update of the weighted graph is ...
Algorithms used by at least two functions of Steiner tree code or its internal helpers.
Declaration of extended graph algorithms.
T makeMinimumSpanningTree(Graph &G, const EdgeArray< T > &weight)
Reduce a graph to its minimum spanning tree (MST) using Kruskal's algorithm.
bool isTree(const Graph &G)
Returns true iff G is a tree, i.e. contains no undirected cycle and is connected.
#define OGDF_ASSERT(expr)
Assert condition expr. See doc/build.md for more information.
T obtainFinalSteinerTree(const EdgeWeightedGraph< T > &G, const NodeArray< bool > &isTerminal, const NodeArray< bool > &isOriginalTerminal, EdgeWeightedGraphCopy< T > *&finalSteinerTree)
T constructTerminalSpanningTreeUsingVoronoiRegions(EdgeWeightedGraphCopy< T > &terminalSpanningTree, const EdgeWeightedGraph< T > &graph, const List< node > &terminals)
The namespace for all OGDF objects.
@ tree
for every hyperedge e a minimal subcubic tree connecting all hypernodes incident with e together is a...
Declaration of simple graph algorithms.
static bool shouldUseErickson(int n, int m)
Returns true iff the rule of thumb predicts to use the algorithm by Erickson et al instead of the Dre...