From 3b02ec985f72bba9596f9571b69080fec7a2b54b Mon Sep 17 00:00:00 2001 From: Matteo Cypriani Date: Fri, 4 Jul 2008 09:27:51 +0000 Subject: [PATCH] Encore gestion topologie MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit server.{hh,cc} : * Ajout des fonctions selectDistances() et computeEuclideanDistances() qui servent à calculer les matrices temporaires de distances entre E_current et E_previous, pour Viterbi. * Adaptation de fastViterbiLike() et monitorClient() pour utiliser ces fonctions. * Corrections mineures. git-svn-id: https://pif.pu-pm.univ-fcomte.fr/svn/loc@49 785a6c6c-259e-4ff1-8b91-dc31627914f0 --- GuiNuMo-server/server.cc | 116 +++++++++++++++++++++++++++------------ GuiNuMo-server/server.hh | 13 ++++- 2 files changed, 90 insertions(+), 39 deletions(-) diff --git a/GuiNuMo-server/server.cc b/GuiNuMo-server/server.cc index 8536af2..904c104 100644 --- a/GuiNuMo-server/server.cc +++ b/GuiNuMo-server/server.cc @@ -236,7 +236,7 @@ Server::Server(const string &ip_addr, const int &listen_port) makeReferencePointListFromFile(DEFAULT_REF_POINT_FILE) ; // Initialisation de "reference_point_list". if (! checkTopology()) // Vérifications. - exit 1 ; // Si problème, on quitte. + exit(1) ; // Si problème, on quitte. makeReferencePointDistances() ; // Initialisation de "reference_point_matrix". makeApListFromFile(DEFAULT_AP_FILE) ; // Initialisation de "access_point_list". @@ -1607,25 +1607,34 @@ void Server::makeWaypointListFromFile(const string &filename) } #ifdef DEBUG - cout << "--> Liste des points de passage (" << nb_pts << ") :" << endl ; fflush(stdout); + cout << "Traitement des points de passage (" << nb_pts << ")..." ; #endif // DEBUG +#ifdef DEBUG_2 + cout << "--> Liste des points de passage (" << nb_pts << ") :" << endl ; fflush(stdout); +#endif // DEBUG_2 /* Initialisation (voisinage de premier ordre de chaque point */ for (set::iterator it = point_list.begin() ; it != point_list.end() ; it++, cur_idx++) // Pour chaque point enregistré { #ifdef DEBUG - cout << *it << " :" ; + if (cur_idx % 100 == 0) + printf("\n%5d", cur_idx) ; + cout << '.' ; + fflush(stdout) ; #endif // DEBUG +#ifdef DEBUG_2 + cout << *it << " :" ; +#endif // DEBUG_2 waypoint_list.push_back(*it) ; // Ajout du point dans waypoint_list waypoint_matrix[cur_idx][cur_idx] = 0 ; // La distance du point à lui-même est nulle for (unsigned int k = 0 ; k < cur_idx ; k++) // Pour chacun des point précédent { -#ifdef DEBUG +#ifdef DEBUG_2 cout << " / " << waypoint_list[k] ; -#endif // DEBUG +#endif // DEBUG_2 if (inTheSameArea(waypoint_list[cur_idx], waypoint_list[k])) // Si le point est dans la même zone, { float dist = it->distance(waypoint_list[k]) ; // on calcule la distance @@ -1634,11 +1643,15 @@ void Server::makeWaypointListFromFile(const string &filename) } } -#ifdef DEBUG +#ifdef DEBUG_2 cout << " /" << endl ; -#endif // DEBUG +#endif // DEBUG_2 } +#ifdef DEBUG + cout << endl ; +#endif // DEBUG + #ifdef DEBUG_2 /* Premier affichage de la matrice */ cout << "--> Matrice des distances entre points de passage (après initialisation) :\n\t\t|" ; @@ -1685,7 +1698,7 @@ void Server::makeWaypointListFromFile(const string &filename) } -#ifdef DEBUG +#ifdef DEBUG_2 /* Deuxième affichage de la matrice */ cout << "--> Matrice des distances entre points de passage :\n\t\t|" ; for (unsigned int k = 0 ; k < nb_pts ; k++) @@ -1699,7 +1712,7 @@ void Server::makeWaypointListFromFile(const string &filename) cout << endl ; } cout << endl ; -#endif // DEBUG +#endif // DEBUG_2 #ifdef DEBUG_T @@ -1847,18 +1860,25 @@ void Server::makeReferencePointDistances() } #ifdef DEBUG - cout << "--> Liste des points de référence (" << nb_pts << ") :" << endl ; fflush(stdout); + cout << "Traitement des points de référence (" << nb_pts << ")..." ; #endif // DEBUG +#ifdef DEBUG_2 + cout << "--> Liste des points de référence (" << nb_pts << ") :" << endl ; fflush(stdout); +#endif // DEBUG_2 /* Calcul des distances */ for (unsigned int cur_idx = 0 ; cur_idx < nb_pts ; cur_idx++) { #ifdef DEBUG - cout << (Point) reference_point_list[cur_idx] ; + if (cur_idx % 100 == 0) + printf("\n%5d", cur_idx) ; + cout << '.' ; + fflush(stdout) ; +#endif // DEBUG #ifdef DEBUG_2 + cout << (Point) reference_point_list[cur_idx] ; cout << " :" ; #endif // DEBUG_2 -#endif // DEBUG reference_point_matrix[cur_idx][cur_idx] = 0 ; // La distance du point à lui-même est nulle @@ -1873,15 +1893,14 @@ void Server::makeReferencePointDistances() reference_point_matrix[k][cur_idx] = dist ; // dans les deux sens. } -#ifdef DEBUG #ifdef DEBUG_2 - cout << " /" ; + cout << " /" << endl ; #endif // DEBUG_2 - - cout << endl ; -#endif // DEBUG } +#ifdef DEBUG + cout << endl ; +#endif // DEBUG #ifdef DEBUG_2 /* Affichage de la matrice */ @@ -1907,6 +1926,32 @@ void Server::makeReferencePointDistances() +/* Place dans "matrix" les distances entre les points de "l1" et de "l2", en les cherchant dans "reference_point_matrix". + */ +void Server::selectDistances(float_array *matrix, const vector &l1, const vector &l2) const +{ + matrix->resize(boost::extents[l1.size()][l2.size()]) ; + + for (unsigned int i = 0 ; i < l1.size() ; i++) + for (unsigned int j = 0 ; j < l2.size() ; j++) + (*matrix)[i][j] = reference_point_matrix[pointIndex(l1[i])][pointIndex(l2[j])] ; +} + + + +/* Calcule et place dans "matrix" les distances euclidiennes entre les points de "l1" et de "l2". + */ +void Server::computeEuclideanDistances(float_array *matrix, const vector &l1, const vector &l2) const +{ + matrix->resize(boost::extents[l1.size()][l2.size()]) ; + + for (unsigned int i = 0 ; i < l1.size() ; i++) + for (unsigned int j = 0 ; j < l2.size() ; j++) + (*matrix)[i][j] = l1[i].distance(l2[j]) ; +} + + + /* FONCTION POUR RÉTRO-COMPATIBILITÉ * Affiche la liste des points de référence (reference_point_list). */ void Server::printReferencePointList() @@ -1941,7 +1986,7 @@ void Server::printPointList(vector &point_list) -void Server::printAccessPointList() +void Server::printAccessPointList() const { #ifdef DEBUG_T cout << "//--> Server::printAccessPointList()" << endl ; fflush(stdout) ; @@ -2085,13 +2130,6 @@ void Server::monitorClient(const unsigned int &client_id, const ALGORITHM &algo) cout << "//--> Server::monitorClient()" << endl ; fflush(stdout) ; #endif // DEBUG_T - Point pointFastViterbi; - vector friisFromList; - - vector - &E_current = client_list[client_id].getRef_viterbi_Ecurrent(), - &E_previous = client_list[client_id].getRef_viterbi_Eprevious() ; - if (VITERBI_N < 2) { cerr << "monitorClient() : N ne peut être inférieur à 2 !" << endl ; @@ -2101,6 +2139,12 @@ void Server::monitorClient(const unsigned int &client_id, const ALGORITHM &algo) return ; } + vector + &E_current = client_list[client_id].getRef_viterbi_Ecurrent(), + &E_previous = client_list[client_id].getRef_viterbi_Eprevious() ; + Point position ; + float_array dst_matrix ; + vector friisFromList; #ifdef TEST vector peregrination_point_list ; @@ -2153,14 +2197,16 @@ void Server::monitorClient(const unsigned int &client_id, const ALGORITHM &algo) switch (algo) { case ALGO_VLI : /* Application de l'algorithme Viterbi */ - fastViterbiLike(client_id, NULL) ; + computeEuclideanDistances(&dst_matrix, E_previous, E_current) ; // On précalcule les distances entre les points de E_previous et E_current. + position = fastViterbiLike(client_id, dst_matrix) ; break ; case ALGO_BASIC_FRBHM : /* Application de l'algorithme FRBHM basique */ cout << "-------FRBHM---------" << endl ; computeFriisFromRefList() ; - pointFastViterbi = fastViterbiLike(client_id, NULL) ; - friisFromList = computeFriisFromRefList(pointFastViterbi, vm) ; + selectDistances(&dst_matrix, E_previous, E_current) ; // On récupère une sous-matrice de reference_point_matrix avec les distances entre les points de E_previous et E_current. + position = fastViterbiLike(client_id, dst_matrix) ; + friisFromList = computeFriisFromRefList(position, vm) ; fbcm_friis(vm, friisFromList) ; break ; @@ -2185,16 +2231,14 @@ void Server::monitorClient(const unsigned int &client_id, const ALGORITHM &algo) * Returns the solution (Point) of the last ended viterbi. * Distances are grouped by line corresponding to an instance. */ -Point Server::fastViterbiLike(const unsigned int &client_id, float **distance_matrix) +Point Server::fastViterbiLike(const unsigned int &client_id, const float_array &distance_matrix) { #ifdef DEBUG_T cout << "//--> Server::fastViterbiLike()" << endl ; fflush(stdout) ; #endif // DEBUG_T float_array &V = client_list[client_id].getRef_viterbi_V() ; - vector - &E_current = client_list[client_id].getRef_viterbi_Ecurrent(), - &E_previous = client_list[client_id].getRef_viterbi_Eprevious() ; + vector &E_current = client_list[client_id].getRef_viterbi_Ecurrent() ; unsigned int &i = client_list[client_id].getRef_viterbi_iteration() ; int N = VITERBI_N, K = VITERBI_K ; @@ -2208,10 +2252,10 @@ Point Server::fastViterbiLike(const unsigned int &client_id, float **distance_ma for (float_index n = N-1-i ; n < N-2 ; n++) // Pour chaque historique existant (sauf le dernier), for (float_index k = 0 ; k < K ; k++) // pour chaque point de l'historique, { // on met à jour le chemin minimum entre l'historique précédent et le point : - V[n][k] = V[n+1][0] + E_previous[0].distance(E_current[k]) ; + V[n][k] = V[n+1][0] + distance_matrix[0][k] ; for (float_index l = 1 ; l < K ; l++) { - float f = V[n+1][l] + E_previous[l].distance(E_current[k]) ; + float f = V[n+1][l] + distance_matrix[l][k] ; if (f < V[n][k]) V[n][k] = f ; } @@ -2220,10 +2264,10 @@ Point Server::fastViterbiLike(const unsigned int &client_id, float **distance_ma /* Traitement du dernier historique */ for (float_index k = 0 ; k < K ; k++) // Pour chaque point, { // on récupère le chemin minimum entre l'historique précédent et le point : - V[N-2][k] = E_previous[0].distance(E_current[k]) ; + V[N-2][k] = distance_matrix[0][k] ; for (float_index l = 1 ; l < K ; l++) { - float f = E_previous[l].distance(E_current[k]) ; + float f = distance_matrix[l][k] ; if (f < V[N-2][k]) V[N-2][k] = f ; } diff --git a/GuiNuMo-server/server.hh b/GuiNuMo-server/server.hh index 80f5d0c..8578b5a 100644 --- a/GuiNuMo-server/server.hh +++ b/GuiNuMo-server/server.hh @@ -53,6 +53,10 @@ typedef enum { ALGO_VLI = 1, ALGO_BASIC_FRBHM } ALGORITHM ; class Server { +public : + typedef boost::multi_array float_array ; // On utilise boost::multi_array pour les matrices de distances temporaires. + typedef float_array::index float_index ; + protected: vector client_list ; // Liste des clients connus. map area_list ; // Liste des zones homogènes (pièces). @@ -116,9 +120,12 @@ public: bool checkTopology() ; - void printReferencePointList(); + void selectDistances(float_array *matrix, const vector &l1, const vector &l2) const ; + void computeEuclideanDistances(float_array *matrix, const vector &l1, const vector &l2) const ; + + void printReferencePointList() ; void printPointList(vector &point_list) ; - void printAccessPointList(); + void printAccessPointList() const ; void computeFriisFromRefList(); vector computeFriisFromRefList(const Point &p, const vector &m); @@ -126,7 +133,7 @@ public: unsigned int getNbReferencePoints()const { return reference_point_list.size(); }; void monitorClient(const unsigned int &client_id, const ALGORITHM &algo) ; - Point fastViterbiLike(const unsigned int &id_client, float **distance_matrix) ; + Point fastViterbiLike(const unsigned int &id_client, const float_array &distance_matrix) ; /* For experimentation purpose only ! */ void radar_exp();