int main(int argc, char *argv[]) { unsigned int n = 0; double beta = 0.0; bool verbose = false, correggi = false, shortest = false, l1 = false, l2 = false, linf = false, endpoint = false, interval = false; w_type maxPeso = 100000; string outfile = ""; istringstream converter; GrafoNonOrientatoBetaMetrico_ListaArchi< w_type > grafo; TSPInstance< w_type > problema; TSPWriter< w_type > *writer; ArgumentList args = ArgumentList(argc, argv); if ( argc < 7 || argc > 9 ) { cerr << "Utilizzo: " << args.getFirst() << " [-c] [-v] [-s|-e|-l1|-l2|-li] -n <nodi> -b <beta> <outfile>" << endl; cerr << "\t-c\t : correggi se non beta metrico;" << endl; cerr << "\t-i\t : metrica intervallo (base, base*2beta);" << endl; cerr << "\t-s\t : metrica shortest path;" << endl; cerr << "\t-e\t : metrica endpoint;" << endl; cerr << "\t-l1\t : metrica spazio l1;" << endl; cerr << "\t-l2\t : metrica spazio l2;" << endl; cerr << "\t-li\t : metrica spazio linf;" << endl; cerr << "\t-v\t : verboso." << endl << endl; return -1; } else { cout << args.getFirst() << endl; } verbose = args.getSwitch("-v"); correggi = args.getSwitch("-c"); shortest = args.getSwitch("-s"); interval = args.getSwitch("-i"); endpoint = args.getSwitch("-e"); l1 = args.getSwitch("-l1"); l2 = args.getSwitch("-l2"); linf = args.getSwitch("-li"); converter.str(args.getSwitchArgument("-n")); converter >> n; converter.clear(); converter.str(args.getSwitchArgument("-b")); converter >> beta; if ( n < 2 || beta < 0.5 ) { cerr << "Il numero di nodi del grafo dev'essere maggiore di 2 ed il valore di beta >= 0.5" << endl; return -1; } outfile = args.getFirst(); grafo.clear(); problema.clear(); grafo.setBeta(beta); srand(time(NULL)); if ( interval ) { /* Metrica intervall (base, base*2beta) */ grafo.generaRandom(n); } else if ( shortest ) { /* Metrica shortest path */ for ( unsigned int i(0); i < n; i++ ) { vertice *temp = grafo.aggiungiVertice(); temp->setKey(i); } for ( Grafo< w_type >::vertice_iterator x = grafo.lista_vertici.begin(); x != --(grafo.lista_vertici.end()); x++ ) { Grafo< w_type >::vertice_iterator temp = x; for ( Grafo< w_type >::vertice_iterator y = ++temp; y != grafo.lista_vertici.end(); y++ ) { grafo.aggiungiArco(*x, *y, static_cast< w_type >(1.0 + (maxPeso * (rand() / (RAND_MAX + 1.0))))); } } map< pair<vertice*, vertice*>, w_type > distanze = FloydWarshall(grafo); for ( Grafo< w_type >::vertice_iterator x = grafo.lista_vertici.begin(); x != --(grafo.lista_vertici.end()); x++ ) { Grafo< w_type >::vertice_iterator temp = x; for ( Grafo< w_type >::vertice_iterator y = ++temp; y != grafo.lista_vertici.end(); y++ ) { if ( distanze[pair<vertice*, vertice*>(*x, *y)] < grafo.getPesoArcoCompreso(*x, *y) ) { (grafo.getArcoCompreso(*x, *y))->costo = distanze[pair<vertice*, vertice*>(*x, *y)]; } } } } else if ( endpoint ) { /* Metrica endpoint */ double beta = grafo.getBeta(); double betaC = (pow(beta, 2.0) - pow(1 - beta, 2.0)) / (beta * (1 - beta)); double betaN = (1 - beta) / beta; double betaNx = beta / (1 - beta); arco< w_type > *tempArco = 0, *minArco = 0, *maxArco = 0; for ( unsigned int i(0); i < n; i++ ) { vertice *temp = grafo.aggiungiVertice(); temp->setKey(i); } for ( Grafo< w_type >::vertice_iterator x = grafo.lista_vertici.begin(); x != --(grafo.lista_vertici.end()); x++ ) { bool first = true; Grafo< w_type >::vertice_iterator temp = x; for ( Grafo< w_type >::vertice_iterator y = ++temp; y != grafo.lista_vertici.end(); y++ ) { double Bmin = (2 * pow(beta, 2.0)) / (1 - beta); double Bmax = (1 - beta) / (2 * pow(beta, 2.0)); if ( y == ++(grafo.lista_vertici.begin()) && x == grafo.lista_vertici.begin() ) { tempArco = grafo.aggiungiArco(*x, *y, static_cast< w_type >(1.0 + (maxPeso * (rand() / (RAND_MAX + 1.0))))); minArco = tempArco; maxArco = tempArco; } else { tempArco = grafo.aggiungiArco(*x, *y, static_cast< w_type >(1.0 + (maxPeso * (rand() / (RAND_MAX + 1.0))))); tempArco->costo = static_cast< w_type >((tempArco->costo * betaC) + betaN); if ( first ) { Grafo< w_type >::vertice_iterator tempVertice = x; tempArco->costo *= grafo.getPesoArcoCompreso(*(--tempVertice), *x); first = false; } else { Grafo< w_type >::vertice_iterator tempVertice = y; tempArco->costo *= grafo.getPesoArcoCompreso(*x, *(--tempVertice)); } if ( grafo.sonoArchiAdiacenti(tempArco, minArco) ) { Bmin = betaNx; } if ( grafo.sonoArchiAdiacenti(tempArco, maxArco) ) { Bmax = betaN; } if ( tempArco->costo > (Bmin * minArco->costo) || tempArco->costo < (Bmax * maxArco->costo) ) { tempArco->costo = static_cast< w_type >(floor((Bmax * maxArco->costo) + (((Bmin * minArco->costo) - (Bmax * maxArco->costo)) * (rand() / (RAND_MAX + 1.0))))); } if ( tempArco-> costo > maxArco->costo ) { maxArco = tempArco; } if ( tempArco->costo < minArco->costo ) { minArco = tempArco; } } } } } else { Space< w_type > spazio; map< vertice *, Point * > verticeToPoint; for ( unsigned int i(0); i < n; i++ ) { vertice *temp = grafo.aggiungiVertice(); temp->setKey(i); verticeToPoint[temp] = spazio.addPoint(static_cast< w_type >(1.0 + (maxPeso * (rand() / (RAND_MAX + 1.0)))), static_cast< w_type >(1.0 + (maxPeso * (rand() / (RAND_MAX + 1.0))))); } for ( Grafo< w_type >::vertice_iterator v = grafo.lista_vertici.begin(); v != --(grafo.lista_vertici.end()); v++ ) { Grafo< w_type >::vertice_iterator temp = v; for ( Grafo< w_type >::vertice_iterator u = ++temp; u != grafo.lista_vertici.end(); u++ ) { if ( l1 ) { /* Metrica spazio l1 */ grafo.aggiungiArco(*v, *u, static_cast< w_type >(spazio.l1Distance(verticeToPoint[*v], verticeToPoint[*u]))); } else if ( l2 ) { /* Metrica spazio l2 */ grafo.aggiungiArco(*v, *u, static_cast< w_type >(spazio.l2Distance(verticeToPoint[*v], verticeToPoint[*u]))); } else if ( linf ) { /* Metrica spazio linf */ grafo.aggiungiArco(*v, *u, static_cast< w_type >(spazio.lInfDistance(verticeToPoint[*v], verticeToPoint[*u]))); } } } } if ( verbose ) { cout << "Grafo generato con n = " << grafo.numVertici() << " ed m = " << grafo.numArchi() << endl; } if ( correggi ) { while ( !grafo.verifyBetaMetric(correggi) ) {}; if ( verbose ) { cout << "Il grafo è risultato " << grafo.getBeta() << "-metrico." << endl; } } problema.setProblemType("TSP"); problema.setEdgeWType("EXPLICIT"); problema.setEdgeWFormat("UPPER_ROW"); problema.setGrafo(&grafo); writer = new TSPWriter< w_type >(&problema); writer->setOutputFile(outfile); if ( !writer->write() ) { cerr << "Si e' verificato un problema durante il salvataggio dell'istanza su file." << endl; delete writer; return 1; } delete writer; if ( verbose ) { cout << "L'istanza e' stata salvata in " << outfile << endl; } return 0; }
int main(int argc, char *argv[]) { bool verbose = false; unsigned int intervalli = 10; /* Argomenti passati all'eseguibile */ ArgumentList args = ArgumentList(argc, argv); if ( argc < 4 || argc > 5 ) { cerr << "Utilizzo: " << args.getFirst() << " [-v] -k <intervalli> <file_istanza_tsp>" << endl; cerr << "\t-k: numero di intervalli;" << endl; cerr << "\t-v : verboso." << endl << endl; return -1; } else { cout << endl << args.getFirst() << endl << endl; } /* Istanza del problema */ TSPInstance< w_type > *problema = new TSPInstance< w_type >; /* Loader dell'istanza */ TSPReader< w_type > *reader = new TSPReader< w_type >(problema); /* Nome del file da cui caricare l'istanza */ string filename = ""; istringstream converter; verbose = args.getSwitch("-v"); converter.str(args.getSwitchArgument("-k")); converter >> intervalli; filename = args.getFirst(); reader->setInputFile(filename); if ( ! reader->read() ) { cerr << "Impossibile leggere l'istanza." << endl; delete problema; delete reader; return -1; } if ( verbose ) { cout << "Istanza caricata, sta per essere eseguito l'algoritmo di calcolo della distribuzione dei pesi." << endl; } /* Mappa contenente gli intervalli di distribuzione dei pesi e le percentuali */ map< double, double > *distribuzione = new map< double, double >(); /* Dimensioni di un intervallo */ double dimBlocco = 0; /* Peso minimo e massimo di un arco */ w_type min = std::numeric_limits< w_type >::max(), max = std::numeric_limits< w_type >::min(); for ( Grafo< w_type >::arco_const_iterator e = (problema->getGrafo())->lista_archi.begin(); e != (problema->getGrafo())->lista_archi.end(); e++ ) { if ( (*e)->costo < min ) { min = (*e)->costo; } if ( (*e)->costo > max ) { max = (*e)->costo; } } if ( verbose ) { cout << "Il peso minimo di un arco e' " << min << " mentre il peso massimo e' " << max << endl; } dimBlocco = (max - min) / static_cast< double >(intervalli); for ( unsigned int i(0); i <= intervalli; i++ ) { distribuzione->insert(pair< double, unsigned int >(min + (i * dimBlocco), 0)); } for ( Grafo< w_type >::arco_const_iterator e = (problema->getGrafo())->lista_archi.begin(); e != (problema->getGrafo())->lista_archi.end(); e++ ) { for ( unsigned int i(1); i <= intervalli; i++ ) { if ( min + (i * dimBlocco) > (*e)->costo ) { ((distribuzione->find(min + ((i - 1) * dimBlocco)))->second)++; break; } } } for ( map< double, double >::iterator i = (distribuzione->begin())++; i != distribuzione->end(); i++ ) { (*i).second = static_cast< double >(((*i).second * 100)) / (problema->getGrafo())->numArchi(); } cout << endl; for ( map< double, double >::iterator i = (distribuzione->begin())++; i != --(distribuzione->end()); i++ ) { cout << fixed << setprecision (2) << "Da " << (*(--i)).first << " a " << (*(++i)).first << ": " << (*i).second << "%" << endl; } cout << endl; return 0; }