예제 #1
0
/*
 * Given a graph and a decomposition, this checks whether or not each edge is
 * contained in at least one bag.  This has the side effect of removing from the
 * graph all those edges of the graph that are in fact contained in some bag.
 * The emptiness of the edge set of the resulting pruned graph is used to decide
 * whether the decomposition has this property.
 */
bool check_edge_coverage(tree_decomposition& T, graph& g)
{
  std::vector<std::pair<unsigned,unsigned> > to_remove;
  /*
   * We go through all bags, and for each vertex in each bag, we remove all its
   * incident edges.  If all the edges are indeed covered by at least one bag,
   * this will leave the graph with an empty edge-set, and it won't if they
   * aren't.
   */
  for(unsigned i = 0; i < T.bags.size() && g.num_edges > 0; i++){
    std::set<unsigned>& it_bag = T.get_bag(i);
    for (std::set<unsigned>::iterator head = it_bag.begin(); head != it_bag.end(); head++) {
      for(auto tail = g.neighbors(*head-1).begin(); tail != g.neighbors(*head-1).end(); tail++) {
        if(it_bag.find(*tail+1) != it_bag.end()) {
          to_remove.push_back(std::pair<unsigned, unsigned>(*head,*tail));
        }
      }
      for (std::vector<std::pair<unsigned, unsigned> >::iterator rem_it = to_remove.begin(); rem_it != to_remove.end(); rem_it++) {
        g.remove_edge(rem_it->first-1,rem_it->second);
      }
      to_remove.clear();
    }
  }

  return (g.num_edges == 0);
}
예제 #2
0
void mst::prim(graph g) {
    int num = g.num_of_vertices();
    minheap* candidates = new minheap(num);
    reset();

    // find the starting point and initialize the heap
    int start_node = 0;
    while(candidates->size() == 0) {
        for(int i=0; i<num; ++i) {
            float c = g.cost(start_node, i);
            if (c != 0) candidates->update(c, i);
        }
        ++start_node;
    }
    closed_set.insert(start_node-1);

    while (candidates->size()!=0) {
        heapitem t = candidates->pop();
        int node = t.get_node();
        // not record the duplicated probed nodes
        if (closed_set.find(node)!=closed_set.end())
            continue;
        closed_set.insert(node);
        path_cost += t.get_key();
        vector<int> n = g.neighbors(node);
        // update the heap with newly found nodes and edges
        for(vector<int>::iterator i=n.begin(); i!=n.end(); ++i) {
            candidates->update(g.cost(node,*i), *i);
        }
    }
    // ckeck if there are isolated nodes
    if (closed_set.size() < num-1) path_cost=-1;
}
예제 #3
0
// calculate the path using dijkstra's algo.
void dijkstra::path(graph g, int u, int v) {
    int num = g.num_of_vertices();
    minheap* candidates = new minheap(num);
    // reset the path_cost and clear the closed_set
    reset();

    // initialize the heap
    // the nodes in the heap are those of "open set"
    for (int i=0; i<num; ++i) {
        float c = g.cost(u, i);
        if (c!=0)
            candidates->update(c, i);
    }

    while (candidates->size()!=0) {
        heapitem t = candidates->pop();
        int node = t.get_node();
        // not record the duplicated probed nodes
        if (closed_set.find(node)!=closed_set.end())
            continue;
        closed_set.insert(node);
        path_cost = t.get_key();
        // terminated if arrives at the destination
        if (node == v)
            return;
        vector<int> n = g.neighbors(node);
        // update the heap with newly found nodes
        for(vector<int>::iterator i=n.begin(); i!=n.end(); ++i) {
            candidates->update(path_cost+g.cost(node,*i), *i);
        }
    }
    // after iteration, the v is not found
    path_cost = -1;
}