main_caixeiro_viajante.cpp

00001 
00002 /*
00003     Este exemplo encontra uma solucao para o problema do caixeiro viajante usando uma rede SOM unidimensional.
00004 
00005         Este programa tem como parametros:
00006                 - o caminho para o arquivo de dados;
00007                 - o raio da vizinhanca (dado como porcentagem);
00008                 - o numero de iteracoes;
00009         
00010         ./somcode <caminho para o arquivo> <raio da vizinhanca> <numero de iteracoes> <tipo de aprendizado>
00011 
00012         Exemplo de chamada do programa: ./somcode ./data/cities.txt 10 1000 batch
00013 
00014         Este e somente um exemplo. Os valores dos parametros devem ser ajustados para cada situacao.
00015         
00016 */
00017 
00018 #pragma warning(disable: 4786)
00019 
00020 #include <cstdlib>
00021 #include <iostream>
00022 #include <vector>
00023 
00024 //inclusao das bibliotecas do somcode necessarias para a execucao do programa
00025 
00026 #include "Som.h"
00027 #include "SOMDataCadastre.h"
00028 #include "MapcodeCadastre.h"
00029 
00030 #include "BatchFactory.h"
00031 #include <string>
00032 
00033 
00034 #include <iomanip.h>
00035 #include <fstream.h>
00036 #include <stdio.h>
00037 
00038 #include "RepositorySOMDataFile.h"
00039 
00040 #include "OneDTFactory.h"
00041 #include "OneDT.h"
00042 
00043 #include "Data.h"  
00044 #include "util.h"
00045 #include "defs.h"
00046 
00047 
00048 using std::cout;
00049 
00050 //criacao dos objetos construtores do padrao abstract factory
00051 
00052 
00053 static BatchFactory fact_batch("Batch");
00054 static OneDTFactory fact_twoD("Two");
00055 
00056 
00057 int main(int argc, char *argv[]) {
00058 
00059   try {         
00060           clock_t c0 = clock();
00061   
00062 
00063           std::vector<std::string> params;
00064           params.push_back(argv[1]);    
00065 
00066           //criacao do objeto da classe concreta que implementa o tipo de acesso a dados atraves de sistema de arquivos
00067           RepositorySOMDataFile repD;
00068           repD.load(params,0);
00069 
00070           //instanciacao do objeto da classe concreta SOMDataCadastre, que serve para isolar os dados dos detalhes de armazenamento
00071           SOMDataCadastre cadD(repD);
00072 
00073           
00074           OneDT* tsp;
00075 
00076 
00077           cout << "Iniciando SOMCode-1.0 ...\n";
00078 
00079           //leitura do arquivo atraves da classe concreta SOMDataCadastre
00080           SOMData* data = cadD.load( std::vector<std::string>() );
00081 
00082           clock_t c1 = clock();
00083 
00084           clock_t c2 = clock();
00085 
00086           SOM* mysom = new SOM();
00087           mysom->setData(data);
00088 
00089 
00100           int dimL, dimC, neig, iter; 
00101          
00102           dimL = data->getDataSize();   // rede neural com numero de neuronios igual ao numero
00103                                         // de cidades de entrada
00104           dimC = 1;                     // por possuir apenas uma dimensao
00105           neig = strtoint(argv[2]);
00106           iter = strtoint(argv[3]);
00107 
00108           mysom->getMapcode()->setNumVar( mysom->getData()->getDimension() );
00109           mysom->getMapcode()->setDimensions( 0, dimL );
00110           mysom->getMapcode()->setDimensions( 1, dimC );
00111 
00112           // tipo de vizinhanca para o problema do caixeiro viajante
00113           mysom->getMapcode()->setLattice( "toro" );   
00114           mysom->getMapcode()->setNeighborType( "bubble" );
00115           mysom->getMapcode()->CreateCodebook( dimL*dimC, mysom->getData()->getDimension() );   
00116 
00117           // nesse problema isto deve ser igual a (numero_de_cidades / 4)
00118           mysom->setInitNeighbor( dimL*(neig*0.01) );  
00119 
00120           // iniciacao colocando os nos em um quadro ao redor das cidades
00121           mysom->setInitType( WINDOW );  
00122 
00123           mysom->setNumIterations( iter );
00124 
00125           if ( strcmp(argv[4],"online") == 0 ){
00126              mysom->setLearningType( ONLINE );
00127              mysom->setLearnType( "Online" );
00128           }
00129 
00130           if ( strcmp(argv[4],"batch") == 0 ) {
00131             mysom->setLearningType( BATCH );
00132             mysom->setLearnType( "Batch" );
00133           }
00134 
00135           /*
00136              Metodos do SOM.
00137           */
00138 
00139          mysom->InitMapcode();  
00140 
00141          string SOM       = "Som" ;
00142          string PATH      = "Path" ;
00143          string INIT_ARRG = "InitialArrangement" ;
00144          string txt       = ".txt" ;
00145         
00146          // nome dos arquivos gerados (arranjo inicial, coordenadas finais dos neuronios e caminha gerado)
00147          // seguindo o padrao:
00148          // <arquivo gerado> N <numero de neuronios> P <porcentagem da vizinhanca> I <numero de iteracoes>
00149 
00150          string nick1 = INIT_ARRG + 'N' + inttostr(dimL) + 'P' + argv[2] + 'I' + argv[3] + txt ;
00151 
00152          tsp = new OneDT(mysom->getMapcode()->getTopolParams());
00153 
00154          // Gera o arquivo com o arranjo inicial dos neuronios (antes do treinamento)
00155          cout << "\nArquivo contendo o arranjo inicial : \n\t" ;
00156          tsp->Save(mysom->getMapcode()->getCodebook() , nick1 , dimL); 
00157          cout << "\n" ;
00158 
00159          mysom->Learning();             
00160          mysom->Quality();
00161 
00162           
00167           clock_t c3 = clock();
00168           cout << "Erro de quantizacao = " << mysom->getQuantizationError() << std::endl;
00169           cout << "Erro topologico = " << mysom->getTopologicalError() << std::endl;
00170           cout << "Tempo decorrido para carregar os dados = " << (float) (c1 - c0)/CLOCKS_PER_SEC << std::endl;
00171           cout << "Tempo decorrido para processar os dados = " << (float) (c3 - c2)/CLOCKS_PER_SEC << std::endl;
00172 
00173 
00174           mysom->Labeling();
00175 
00176           TLabel label = mysom->getMapcode()->getLabel();
00177 
00178         // impressao das coordenadas das cidades. 
00179         // descomentar se necessario
00180         /*
00181           int tsp_count = 1 ;
00182           for (int i = 0; i < label.size() ; i++) {
00183              cout << i+1 << ": " ;
00184              for (int j = 0; j < label[i].size(); j++){
00185                 cout << mysom->getCities()[strtoint(rem_id(label[i][j]))][1] ;
00186                 cout << "," << mysom->getCities()[strtoint(rem_id(label[i][j]))][2] << " " ;
00187                 tsp_count++ ;
00188                 }
00189              cout << "\n";
00190           }
00191          */
00192         
00193          string nick2, nick3 ;
00194          
00195          // nome dos arquivos gerados (arranjo inicial, coordenadas finais dos neuronios e caminha gerado)
00196          // seguindo o padrao:
00197          // <arquivo gerado> N <numero de neuronios> P <porcentagem da vizinhanca> I <numero de iteracoes>
00198          
00199          nick2 = PATH + 'N' + inttostr(dimL) + 'P' + argv[2] + 'I' + argv[3] + txt ;
00200          nick3 = SOM + 'N' + inttostr(dimL) + 'P' + argv[2] + 'I' + argv[3] + txt ;
00201 
00202 
00203          TMatrix path = tsp->Extract_Path(mysom->getMapcode()->getLabel() , mysom->getCities() , dimL) ;
00204 
00205          cout << "\nArquivo contendo o caminho gerado : \n\t" ;
00206          tsp->Save(path , nick2 , dimL);
00207          cout << "\nArquivo contendo as coordenadas dos neuronios : \n\t" ;
00208          tsp->Save(mysom->getMapcode()->getCodebook() , nick3 , dimL);
00209 
00210 
00211   } catch(std::exception& ex) {
00212     cout << ex.what() << std::endl;
00213   }
00214       
00215   return EXIT_SUCCESS;
00216   
00217 };

Generated on Tue Aug 7 16:03:33 2007 for SOMCode by  doxygen 1.5.3