| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587 | 
							- #include <fstream>
 - #include <iostream>
 - #include <string>
 - #include <vector>
 - #include <cmath>
 - #include <cstdlib>
 - #include <cstring>
 - #include "Stopwatch.h"
 - #include "ArrayGraph.h"
 - #include "ListGraph.h"
 - 
 - using namespace std;
 - 
 - // USTAWIENIA
 - // Liczba powtorzen automatycznych pomiarow do usrednienia
 - const int measureIterations = 10;
 - // liczba automatycznych pomiarow
 - const int measureNumber = 4;
 - // Czas zatrzymania algorytmu tabu search w kazdym z automatycznych pomiarow
 - const int measureTabuStop[4] = {1, 5, 10, 15};
 - // Maksymalna odleglosc miast przy automatycznym generowaniu
 - const int measureSalesmanDistance = 400;
 - 
 - // Wykorzystanie reprezentacji grafu w postaci list sasiedztwa...
 - // ...zamiast (domyslnie) macierzy sasiedztwa
 - // (wolniejsze obliczenia, mniejsze uzycie pamieci)
 - bool useListGraph = false;
 - 
 - // Domyslna kadencja tabu search - wybor automatyczny
 - unsigned tabuLength = 0;
 - // Domyslny stan dywersyfikacji
 - bool tabuDiversification = true;
 - // Domyslne kryterium dywersyfikacji, liczba iteracji bez poprawy
 - int tabuIterationsToRestart = 10000;
 - // Domyslny czas zatrzymania algorytmu tabu search [s]
 - unsigned tabuStopTime = 60;
 - 
 - // Domyslna liczba watkow tabu search
 - unsigned tabuThreadsNumber = 2;
 - 
 - int main(int argc, char *argv[])
 - {
 -     Stopwatch clock;                // czasomierz
 -     Graph *graph = NULL;            // <- tu bedziemy zapisywac adresy przez caly program
 - 
 -     if(argc > 1)
 -     {
 -         for(int i = 1; i < argc; i++)
 -         {
 -             if(strcmp(argv[i], "-l") == 0)
 -             {
 -                 useListGraph = true;
 -             }
 -             else if(strcmp(argv[i], "-t") == 0)
 -             {
 -                 i++;
 -                 int input = atoi(argv[i]);
 - 
 -                 if(input > 0)
 -                     tabuThreadsNumber = input;
 -                 else
 -                     cout << "+++ MELON MELON MELON +++ Nieprawidlowa liczba watkow +++" << endl << endl;
 -             }
 -         }
 -     }
 - 
 -     cout << "PEA Projekt 2 Plus v2.0ALPHA" << endl;
 -     cout << "Jan Potocki 2017-2019" << endl;
 -     cout << "(beerware)" << endl;
 -     if(useListGraph)
 -         cout << "Uzycie listowej reprezentacji grafu" << endl;
 -     else
 -         cout << "Uzycie macierzowej reprezentacji grafu" << endl;
 -     cout << endl;
 - 
 -     int salesmanSelection;
 -     do
 -     {
 -         cout << "1. Wygeneruj losowe dane" << endl;
 -         cout << "2. Wyswietl dane" << endl;
 -         cout << "3. Ustawienia TS" << endl;
 -         cout << "4. Tabu search" << endl;
 -         cout << "5. Podzial i ograniczenia" << endl;
 -         cout << "6. Przeglad zupelny" << endl;
 -         cout << "7. Automatyczne pomiary (tabu search)" << endl;
 -         cout << "8. Wczytaj dane z pliku TSPLIB FULL_MATRIX" << endl;
 -         cout << "9. Wczytaj dane z pliku TSPLIB EUC_2D" << endl;
 -         cout << "Aby zakonczyc - 0" << endl;
 -         cout << "Wybierz: ";
 -         cin >> salesmanSelection;
 -         cout << endl;
 - 
 -         switch(salesmanSelection)
 -         {
 -             case 1:
 -             {
 -                 int vertex;
 -                 cout << "Liczba miast: ";
 -                 cin >> vertex;
 -                 cout << endl;
 - 
 -                 if(graph != NULL)
 -                     delete graph;
 - 
 -                 if(useListGraph)
 -                     graph = new ListGraph(vertex);
 -                 else
 -                     graph = new ArrayGraph(vertex);
 - 
 -                 Graph::randomGenerateFullGraph(*graph, measureSalesmanDistance);
 -             }
 -             break;
 -             case 2:
 -             {
 -                 if(graph != NULL)
 -                     graph->displayGraph();
 -                 else
 -                     cout << "Brak wygenerowanych danych" << endl;
 -                 cout << endl;
 -             }
 -             break;
 -             case 3:
 -             {
 -                 int settingsSelection;
 -                 do
 -                 {
 -                     if(tabuDiversification == true)
 -                         cout << "1. Przelacz dywersyfikacje" << "\t" << "(wlaczona)" << endl;
 -                     else
 -                         cout << "1. Przelacz dywersyfikacje" << "\t" << "(wylaczona)" << endl;
 - 
 -                     cout << "2. Kryterium dywersyfikacji" << "\t" << "(" << tabuIterationsToRestart << " iteracji)" << endl;
 - 
 -                     if(tabuLength == 0)
 -                         cout << "3. Kadencja na liscie tabu" << "\t" << "(auto)" << endl;
 -                     else
 -                         cout << "3. Kadencja na liscie tabu" << "\t" << "(" << tabuLength << ")" << endl;
 - 
 -                     cout << "4. Czas zatrzymania" << "\t\t" << "(" << tabuStopTime << " s)" << endl;
 -                     cout << "Powrot - 0" << endl;
 -                     cout << "Wybierz: ";
 -                     cin >> settingsSelection;
 -                     cout << endl;
 - 
 -                     switch(settingsSelection)
 -                     {
 -                         case 1:
 -                         {
 -                             tabuDiversification = !tabuDiversification;
 - 
 -                             if(tabuDiversification == true)
 -                                 cout << "Dywersyfikacja zostala wlaczona" << endl;
 -                             else
 -                                 cout << "Dywersyfikacja zostala wylaczona" << endl;
 -                             cout << endl;
 -                         }
 -                         break;
 -                         case 2:
 -                         {
 -                             cout << "Podaj nowa liczbe iteracji bez poprawy: ";
 -                             cin >> tabuIterationsToRestart;
 -                             cout << endl;
 -                         }
 -                         break;
 -                         case 3:
 -                         {
 -                             cout << "Podaj nowa kadencje (0 -> auto): ";
 -                             cin >> tabuLength;
 -                             cout << endl;
 -                         }
 -                         break;
 -                         case 4:
 -                         {
 -                             cout << "Podaj nowy czas pracy [s]: ";
 -                             cin >> tabuStopTime;
 -                             cout << endl;
 -                         }
 -                         break;
 -                         case 0:
 -                         {
 -                         }
 -                         break;
 -                         default:
 -                         {
 -                             cout << "Nieprawidlowy wybor" << endl;
 -                             cout << endl;
 -                         }
 -                     }
 -                 } while(settingsSelection != 0);
 -             }
 -             break;
 -             case 4:
 -             {
 -                 if(graph != NULL)
 -                 {
 -                     if(tabuStopTime != 0)
 -                     {
 -                         unsigned effectiveTabuLength;
 -                         if(tabuLength == 0)
 -                         {
 -                             effectiveTabuLength = (graph->getVertexNumber() / 10) * 10;
 -                             if(effectiveTabuLength == 0)
 -                               effectiveTabuLength = 10;
 -                         }
 -                         else
 -                         {
 -                             effectiveTabuLength = tabuLength;
 -                         }
 - 
 -                         if(tabuLength == 0)
 -                             cout << "Kadencja: " << effectiveTabuLength << " (auto)" << endl;
 -                         else
 -                             cout << "Kadencja: " << effectiveTabuLength << endl;
 - 
 -                         cout << "Czas zatrzymania algorytmu [s]: " << tabuStopTime << endl;
 - 
 -                         if(tabuDiversification == true)
 -                             cout << "Dywersyfikacja wlaczona, kryterium: " << tabuIterationsToRestart << " iteracji bez poprawy" << endl;
 -                         else
 -                             cout << "Dywersyfikacja wylaczona" << endl;
 - 
 -                         cout << "Liczba watkow: " << tabuThreadsNumber << endl;
 -                         cout << endl;
 - 
 -                         clock.start();
 -                         vector<unsigned> route = Graph::travellingSalesmanTabuSearch(*graph, effectiveTabuLength, tabuDiversification, tabuIterationsToRestart, tabuStopTime, tabuThreadsNumber);
 -                         clock.stop();
 - 
 -                         // Wyswietlenie trasy
 -                         unsigned distFromStart = 0;
 -                         unsigned length = 0;
 -                         cout << route.at(0) << '\t' << length << '\t' << distFromStart << endl;
 -                         for(int i = 1; i < route.size(); i++)
 -                         {
 -                             length = graph->getWeight(route.at(i - 1), route.at(i));
 -                             distFromStart += length;
 - 
 -                             cout << route.at(i) << '\t' << length << '\t' << distFromStart << endl;
 -                         }
 - 
 -                         cout << "Dlugosc trasy: " << distFromStart << endl;
 -                         cout << endl;
 -                         cout << "Czas wykonania algorytmu [s]: " << clock.read() << endl;
 -                     }
 -                     else
 -                     {
 -                         // Easter egg ;-)
 -                         cout << "+++ MELON MELON MELON +++ Blad: Brak Sera! +++ !!!!! +++" << endl;
 -                     }
 -                 }
 -                 else
 -                     cout << "+++ MELON MELON MELON +++ Brak zaladowanych danych +++" << endl;
 -                 cout << endl;
 -             }
 -             break;
 -             case 5:
 -             {
 -                 if(graph != NULL)
 -                 {
 -                     clock.start();
 -                     vector<unsigned> route = Graph::travellingSalesmanBranchAndBound(*graph);
 -                     clock.stop();
 - 
 -                     // Wyswietlenie trasy
 -                     unsigned distFromStart = 0;
 -                     unsigned length = 0;
 -                     cout << route.at(0) << '\t' << length << '\t' << distFromStart << endl;
 -                     for(int i = 1; i < route.size(); i++)
 -                     {
 -                         length = graph->getWeight(route.at(i - 1), route.at(i));
 -                         distFromStart += length;
 - 
 -                         cout << route.at(i) << '\t' << length << '\t' << distFromStart << endl;
 -                     }
 - 
 -                     cout << "Dlugosc trasy: " << distFromStart << endl;
 -                     cout << endl;
 -                     cout << "Czas wykonania algorytmu [s]: " << clock.read() << endl;
 -                 }
 -                 else
 -                     cout << "+++ MELON MELON MELON +++ Brak zaladowanych danych +++" << endl;
 -                 cout << endl;
 -             }
 -             break;
 -             case 6:
 -             {
 -                 if(graph != NULL)
 -                 {
 -                     clock.start();
 -                     vector<unsigned> route = Graph::travellingSalesmanBruteForce(*graph);
 -                     clock.stop();
 - 
 -                     // Wyswietlenie trasy
 -                     unsigned distFromStart = 0;
 -                     unsigned length = 0;
 -                     cout << route.at(0) << '\t' << length << '\t' << distFromStart << endl;
 -                     for(int i = 1; i < route.size(); i++)
 -                     {
 -                         length = graph->getWeight(route.at(i - 1), route.at(i));
 -                         distFromStart += length;
 - 
 -                         cout << route.at(i) << '\t' << length << '\t' << distFromStart << endl;
 -                     }
 - 
 -                     cout << "Dlugosc trasy: " << distFromStart << endl;
 -                     cout << endl;
 -                     cout << "Czas wykonania algorytmu [s]: " << clock.read() << endl;
 -                 }
 -                 else
 -                     cout << "+++ MELON MELON MELON +++ Brak zaladowanych danych +++" << endl;
 -                 cout << endl;
 -             }
 -             break;
 -             case 7:
 -             {
 -                 // PEA 2
 -                 // Jan Potocki 2017
 -                 if(graph != NULL)
 -                 {
 -                     unsigned effectiveTabuLength;
 -                     if(tabuLength == 0)
 -                     {
 -                         effectiveTabuLength = (graph->getVertexNumber() / 10) * 10;
 -                         if(effectiveTabuLength == 0)
 -                           effectiveTabuLength = 10;
 -                     }
 -                     else
 -                     {
 -                         effectiveTabuLength = tabuLength;
 -                     }
 - 
 -                     double measureResults[measureNumber], measureResultsDiv[measureNumber];
 -                     for(int i = 0; i < measureNumber; i++)
 -                     {
 -                         measureResults[i] = 0;
 -                         measureResultsDiv[i] = 0;
 -                     }
 - 
 -                     cout << "Pomiary dla problemu komiwojazera, tabu search" << tabuLength << endl;
 - 
 -                     if(tabuLength == 0)
 -                         cout << "Kadencja: " << effectiveTabuLength << " (auto)" << endl;
 -                     else
 -                         cout << "Kadencja: " << effectiveTabuLength << endl;
 - 
 -                     cout << "Kryterium dywersyfikacji: " << tabuIterationsToRestart << " iteracji bez poprawy" << endl;
 -                     cout << "Liczba watkow: " << tabuThreadsNumber << endl;
 - 
 -                     // Petla pomiarowa
 -                     for(int krok = 0; krok < measureIterations; krok++)
 -                     {
 -                         for(int i = 0; i < measureNumber; i++)
 -                         {
 -                             vector<unsigned> route;
 -                             unsigned routeLength;
 - 
 -                             // Bez dywersyfikacji
 -                             cout << "Pomiar " << measureTabuStop[i] << " [s] (" << krok + 1 << " z " << measureIterations << " bez dywersyfikacji)..." << endl;
 - 
 -                             route = Graph::travellingSalesmanTabuSearch(*graph, effectiveTabuLength, false, tabuIterationsToRestart, measureTabuStop[i], tabuThreadsNumber);
 - 
 -                             routeLength = 0;
 -                             for(int j = 1; j < route.size(); j++)
 -                                 routeLength += graph->getWeight(route.at(j - 1), route.at(j));
 -                             measureResults[i] += routeLength;
 - 
 -                             // Z dywersyfikacja
 -                             cout << "Pomiar " << measureTabuStop[i] << " [s] (" << krok + 1 << " z " << measureIterations << " z dywersyfikacja)..." << endl;
 - 
 -                             route = Graph::travellingSalesmanTabuSearch(*graph, effectiveTabuLength, true, tabuIterationsToRestart, measureTabuStop[i], tabuThreadsNumber);
 - 
 -                             routeLength = 0;
 -                             for(int j = 1; j < route.size(); j++)
 -                                 routeLength += graph->getWeight(route.at(j - 1), route.at(j));
 -                             measureResultsDiv[i] += routeLength;
 -                         }
 -                     }
 - 
 -                     cout << "Opracowywanie wynikow..." << endl;
 - 
 -                     for(int i = 0; i < measureNumber; i++)
 -                     {
 -                         measureResults[i] = nearbyint(measureResults[i] / measureIterations);
 -                         measureResultsDiv[i] = nearbyint(measureResultsDiv[i] / measureIterations);
 -                     }
 - 
 -                     cout << "Zapis wynikow..." << endl;
 - 
 -                     ofstream salesmanToFile;
 -                     salesmanToFile.open("wyniki-komiwojazer-ts.txt");
 -                     salesmanToFile << "czas - bez dywersyfikacji - z dywersyfikacja" << endl;
 -                     for(int i = 0; i < measureNumber; i++)
 -                     {
 -                         salesmanToFile << measureTabuStop[i] << " [s]: " << (int)measureResults[i] << ' ' << (int)measureResultsDiv[i] << endl;
 -                     }
 -                     salesmanToFile.close();
 - 
 -                     cout << "Gotowe!" << endl;
 -                     cout << endl;
 -                 }
 -                 else
 -                 {
 -                     cout << "+++ MELON MELON MELON +++ Brak zaladowanych danych +++" << endl;
 -                     cout << endl;
 -                 }
 -             }
 -             break;
 -             case 8:
 -             {
 -                 // Jan Potocki 2017
 -                 string filename, fileInput;
 -                 ifstream salesmanDataFile;
 - 
 -                 cout << "Podaj nazwe pliku: ";
 -                 cin >> filename;
 - 
 -                 salesmanDataFile.open(filename.c_str());
 -                 if(salesmanDataFile.is_open())
 -                 {
 -                     do
 -                         salesmanDataFile >> fileInput;
 -                     while(fileInput != "DIMENSION:");
 - 
 -                     salesmanDataFile >> fileInput;
 -                     int vertex = stoi(fileInput);
 - 
 -                     do
 -                         salesmanDataFile >> fileInput;
 -                     while(fileInput != "EDGE_WEIGHT_FORMAT:");
 - 
 -                     salesmanDataFile >> fileInput;
 -                     if(fileInput == "FULL_MATRIX")
 -                     {
 -                         if(graph != NULL)
 -                             delete graph;
 - 
 -                         if(useListGraph)
 -                             graph = new ListGraph(vertex);
 -                         else
 -                             graph = new ArrayGraph(vertex);
 - 
 -                         do
 -                             salesmanDataFile >> fileInput;
 -                         while(fileInput != "EDGE_WEIGHT_SECTION");
 - 
 -                         for(int i = 0; i < vertex; i++)
 -                         {
 -                             for(int j = 0; j < vertex; j++)
 -                             {
 -                                 salesmanDataFile >> fileInput;
 -                                 int weight = stoi(fileInput);
 - 
 -                                 if(i != j)
 -                                     graph->addEdge(i, j, weight);
 -                             }
 -                         }
 - 
 -                         cout << "Wczytano - liczba wierzcholkow: " << vertex << endl;
 -                         cout << endl;
 -                     }
 -                     else
 -                     {
 -                         cout << "+++ MELON MELON MELON +++ Nieobslugiwany format " << fileInput << " +++" << endl;
 -                         cout << endl;
 -                     }
 - 
 -                     salesmanDataFile.close();
 -                 }
 -                 else
 -                 {
 -                     cout << "+++ MELON MELON MELON +++ Brak pliku " << filename << " +++" << endl;
 -                     cout << endl;
 -                 }
 -             }
 -             break;
 -             case 9:
 -             {
 -                 // Jan Potocki 2017
 -                 string filename, fileInput;
 -                 vector<float> xCoord, yCoord;
 -                 ifstream salesmanDataFile;
 - 
 -                 cout << "Podaj nazwe pliku: ";
 -                 cin >> filename;
 - 
 -                 salesmanDataFile.open(filename.c_str());
 -                 if(salesmanDataFile.is_open())
 -                 {
 -                     do
 -                         salesmanDataFile >> fileInput;
 -                     while(fileInput != "DIMENSION:");
 - 
 -                     salesmanDataFile >> fileInput;
 -                     int vertex = stoi(fileInput);
 - 
 -                     do
 -                         salesmanDataFile >> fileInput;
 -                     while(fileInput != "EDGE_WEIGHT_TYPE:");
 - 
 -                     salesmanDataFile >> fileInput;
 -                     if(fileInput == "EUC_2D")
 -                     {
 -                         if(graph != NULL)
 -                             delete graph;
 - 
 -                         if(useListGraph)
 -                             graph = new ListGraph(vertex);
 -                         else
 -                             graph = new ArrayGraph(vertex);
 - 
 -                         do
 -                             salesmanDataFile >> fileInput;
 -                         while(fileInput != "NODE_COORD_SECTION");
 - 
 -                         for(int i = 0; i < vertex; i++)
 -                         {
 -                             salesmanDataFile >> fileInput;
 - 
 -                             salesmanDataFile >> fileInput;
 -                             xCoord.push_back(stof(fileInput));
 - 
 -                             salesmanDataFile >> fileInput;
 -                             yCoord.push_back(stof(fileInput));
 -                         }
 - 
 -                         // To daloby sie zrobic optymalniej (macierz symetryczna), ale nie chce mi sie ...
 -                         // ..wole zoptymalizować czas programowania ;-)
 -                         for(int i = 0; i < vertex; i++)
 -                         {
 -                             for(int j = 0; j < vertex; j++)
 -                             {
 -                                 if(i != j)
 -                                 {
 -                                     float xDiff = xCoord.at(i) - xCoord.at(j);
 -                                     float yDiff = yCoord.at(i) - yCoord.at(j);
 -                                     int weight = nearbyint(sqrt(xDiff * xDiff + yDiff * yDiff));
 - 
 -                                     graph->addEdge(i, j, weight);
 -                                 }
 -                             }
 -                         }
 - 
 -                         cout << "Wczytano - liczba wierzcholkow: " << vertex << endl;
 -                         cout << endl;
 -                     }
 -                     else
 -                     {
 -                         cout << "+++ MELON MELON MELON +++ Nieobslugiwany format " << fileInput << " +++" << endl;
 -                         cout << endl;
 -                     }
 - 
 -                     salesmanDataFile.close();
 -                 }
 -                 else
 -                 {
 -                     cout << "+++ MELON MELON MELON +++ Brak pliku " << filename << " +++" << endl;
 -                     cout << endl;
 -                 }
 -             }
 -             break;
 -             case 0:
 -             {
 -             }
 -             break;
 -             default:
 -             {
 -                 cout << "Nieprawidlowy wybor" << endl;
 -                 cout << endl;
 -             }
 -         }
 -     } while(salesmanSelection != 0);
 - 
 -     if(graph != NULL)
 -         delete graph;
 - 
 -     cout << "Konczenie..." << endl;
 -     // Easter egg :-P
 -     cout << '"' << "Myslak Stibbons niepokoil sie HEX-em." << endl;
 -     cout << "Nie wiedzial, jak dziala, chociaz wszyscy uwazali, ze wie." << endl;
 -     cout << "Oczywiscie, calkiem niezle orientowal sie w niektorych elementach;" << endl;
 -     cout << "byl tez pewien, ze HEX mysli o problemach, przeksztalcajac je" << endl;
 -     cout << "w liczby i mielac ..." << '"' << endl;
 -     cout << "(Terry Pratchett, " << '"' << "Wiedzmikolaj" << '"' << ", tlumaczenie Piotr Cholewa)" << endl;
 -     cout << endl;
 - 
 -     return 0;
 - }
 
 
  |