So I am implementing a Benders procedure using lazy constraints from GUROBI. As part of the subproblem procedure I need to process a graph using Breadth First Search, for which I am using LEMON. I am trying to implement use a visitor for the BFS search. However when I try to access the map of reached nodes using bfs.reached() I get a compiler (I suppose) error.
Here is the callback class implementation so far:
typedef ListDigraph::Node Node;
typedef ListDigraph::Arc Arc;
typedef ListDigraph::ArcMap<double> ArcDou;
typedef ListDigraph::NodeMap<double> NodeDou;
typedef ListDigraph::ArcMap<int> ArcInt;
typedef ListDigraph::ArcMap<bool> ArcBool;
typedef ListDigraph::NodeMap<int> NodeInt;
typedef ListDigraph::NodeIt NodeIt;
typedef ReverseDigraph<ListDigraph>::NodeIt NodeIt_rev;
typedef ListDigraph::ArcIt ArcIt;
class BendersSub: public GRBCallback
{
public:
const Instance_data &ins;
const vec4GRBVar &X;
const vec1GRBvar &u;
vec2GRBVar &p;
GRBModel &modelSubD;
BendersSub(const Instance_data &ins, const vec4GRBVar &X, const vec1GRBvar &u, vec2GRBVar &p, GRBModel &modelSubD)
:ins(ins), X(X), u(u), p(p),modelSubD(modelSubD){
//cout << "\n\tI:" << ins.I << " J:" << ins.J << " T:" << ins.T << " V:" << ins.V << flush;
}
protected:
void callback() {
try {
if (where == GRB_CB_MIPSOL) {
cout << "\n -- Entering Callback -- " << flush;
string var_name;
int I = ins.I , J = ins.I , T = ins.T , V = ins.V,i,j,k,t,v;
ListDigraph grafo;
Node x;
for( int t(0); t < ins.T+1; t++)
for ( int i(0); i < ins.I; i++)
x = grafo.addNode();
Arc arco;
int count( 0 );
for(t = 0; t < ins.T; ++t){
for(i = 0; i < ins.I; ++i){
for(j = 0; j < ins.J; ++j){
if ( i == j ){
arco = grafo.addArc(grafo.nodeFromId(i + ins.I * t),grafo.nodeFromId(j + (ins.I * (t+1))));
}else if ( (t + ins.tau.at(i).at(j)) <= ins.T-1 ){
arco = grafo.addArc(grafo.nodeFromId(i + ins.I * t),grafo.nodeFromId(j + ins.I * (t + ins.tau.at(i).at(j))));
}
else if ( (t + ins.tau.at(i).at(j)) > ins.T-1 ){
arco = grafo.addArc(grafo.nodeFromId(i + ins.I * t),grafo.nodeFromId(((ins.I*(ins.T+1)+1))-1-(ins.I)+j)) ;
}
}
}
}
NodeDou divergence (grafo);
ArcDou costo (grafo);
ArcBool filter (grafo, true);
NodeDou potential (grafo);
ReverseDigraph<ListDigraph> grafo_r(grafo);
using Visitor = Visitor_AcSup<NodeDou>;
for ( int v(0); v < V; v++){
double sum_sup(0.0);
Visitor visitor(grafo_r, divergence, sum_sup);
cout << "\nsum_sup: " << sum_sup << flush;
for (t = 0; t < T; t++){
for(i = 0; i < I ; i++){
if(divergence[grafo.nodeFromId(flat_ixt(ins,t,i))] < -EPS3){
BfsVisit<ReverseDigraph<ListDigraph>, Visitor> bfs(grafo_r,visitor);
bfs.run(grafo.nodeFromId(flat_ixt(ins,t,i)));
if( (sum_sup-fabs(divergence[grafo.nodeFromId(flat_ixt(ins,t,i))])) < -EPS4 ){
cout << "\nBuild Ray" << flush;
}
}
}
}
for (NodeIt_rev u(grafo_r); u != INVALID; ++u){
/*The error does not show when I comment this line.*/
cout << "\nId: " << grafo.id(u) << setw(10) << bfs.reached(u) << flush;
}
cout << "\nsum_sup: " << sum_sup << flush;
.
/* Remaining code */
.
.
}/*end_if v*/
//cout << "\n -- Exiting Callback -- " << flush;
}
}catch (GRBException e) {
cout << "Error number: " << e.getErrorCode() << endl;
cout << e.getMessage() << endl;
exit(EXIT_FAILURE);
}catch (const exception &exc){
cerr << "\nCallback - " << exc.what() << flush;
exit(EXIT_FAILURE);
}catch (...) {
cout << "Error during callback" << endl;
exit(EXIT_FAILURE);
}
}
};
Here is the (incomplete visitor) implementation.
template <typename DivMap >
class Visitor_AcSup : public BfsVisitor< const ReverseDigraph<ListDigraph> > {
public:
Visitor_AcSup(const ReverseDigraph<ListDigraph>& _graph, DivMap& _dirMap, double& _sum_sup)
: graph(_graph), dirMap(_dirMap), sum_sup(_sum_sup){
cout << "\n --Calling constructor of Visitor_AcSup -- " << endl;
sum_sup = 0.0;
}
void start (const Node &node){
//cout << "\nstart Node: " << graph.id(node) << flush;
sum_sup -= dirMap[node];
}
void reach (const Node &node){
//cout << "\nReach Node: " << graph.id(node) << flush;
}
void process (const Node &node){
//cout << "\nProcess Node: " << graph.id(node) << setw(5) << dirMap[node] << flush;
sum_sup += dirMap[node];
}
void discover(const Arc& arc) {
//cout << "\tDiscover Arc: " << graph.id(arc) << flush;
}
void examine(const Arc& arc) {
//cout << "\tExamine Arc: " << graph.id(arc) << flush;
}
private:
const ReverseDigraph<ListDigraph>& graph;
DivMap& dirMap;
double& sum_sup;
The error looks like this
functions.cpp:1845:59: error: overloaded function with no contextual type information
cout << "\nId: " << grafo.id(u) << setw(10) << bfs.reached(u) << flush;
^~~~~~~
Makefile:27: recipe for target 'VAP' failed
I am clueless about what is happening as the only error that comes up to my mind is conflict of keywords between namespaces
using namespace lemon;
using namespace lemon::concepts;
using namespace std;
but have found no resolution to this. I am a newbie in C++, so that I am asking you guys where this could possibly come from.