Les matrices facilement ?

Les matrices facilement ? - C++ - Programmation

Marsh Posté le 14-11-2005 à 16:57:04    

J'ai besoin de manipuler des matrices dans un projet C++ et comme je voudrais pas réinventer la roue, je cherche une bonne biblio pour cette structure de base... Y'en a dans STDLIB ? Ailleurs ?
 
Merci d'avance !

Reply

Marsh Posté le 14-11-2005 à 16:57:04   

Reply

Marsh Posté le 14-11-2005 à 17:37:24    

Pour du c++, tu peux regarder du coté de la lib boost::numeric::ublas
http://www.boost.org/

Reply

Marsh Posté le 14-11-2005 à 17:41:23    

Kyle_Katarn a écrit :

J'ai besoin de manipuler des matrices dans un projet C++ et comme je voudrais pas réinventer la roue, je cherche une bonne biblio pour cette structure de base... Y'en a dans STDLIB ? Ailleurs ?

 

Merci d'avance !


Quelle taille, tes matrices ? Quelle utilisation ?
Voici un petit template maison pour des matrices jusqu'à, disons 500x500. Au delà, une vraie lib est nécessaire.
Simple et utilisable immédiatement, il est facile de l'étendre avec des fonctions de multiplication, etc.
On peut définir une matrice M(20,20) (matrice 20x20), faire une copie, genre : N = M, appliquer une fonction à tous les éléments de la matrice, etc.
Il manque des opérations essentielles comme la multiplication, la transposition et l'inversion, mais ça devrait être facile à implémenter soi-même avec cette base.

Code :
  1. #ifndef _CLASSE_Matrice_
  2. #define _CLASSE_Matrice_
  3. #include<vector>
  4. //#include<ostream>
  5. using namespace std;
  6. template <typename T>
  7. class Matrice
  8. {
  9. public:
  10.     /// constructeurs/destructeur
  11. Matrice(const int l, const int c, const T val = 0): _iL(l), _iC(c) {
  12.  _v.resize(l * c, val);
  13. }
  14.    
  15.     Matrice(const int l, const int c, const T* tab): _iL(l), _iC(c) {
  16.         _v.resize(l * c);
  17.         for( int l = 0; l < _iL; l++ )
  18.          for( int c = 0; c < _iC; c++ )
  19.       _v[ l*_iC + c ] = tab[ l*_iC + c ];
  20.     }
  21.     Matrice(const Matrice &rhs): _iL(rhs.X()), _iC(rhs.Y()) {
  22.         _v.resize(_iL * _iC);
  23.             for( int l = 0; l < _iL; l++ )
  24.             for( int c = 0; c < _iC; c++ )
  25.                     _v[ l*_iC + c ] = rhs(l, c);
  26.     }
  27.    
  28. ~Matrice(){}
  29. /// @brief accesseurs
  30. inline T operator()(const int l, const int c) const {
  31.             return _v[l * _iC + c];
  32. }
  33. inline T& operator()(const int l, const int c) {
  34.               return _v[l * _iC + c];
  35. }
  36.         inline T getVal(int x, int y) const {
  37.               return _v[ x * _iC + y ];
  38.         }
  39.         inline void setVal(int x, int y, T val) {
  40.               _v[ x * _iC + y ] = val;
  41.         }
  42.    
  43.     inline int X() const { return _iL; }
  44.     inline int Y() const { return _iC; }
  45.     /// opérations sur la classe
  46.    
  47.     /// @brief operateur d'assignation
  48. T& operator=(const T& rhs) {
  49.  if (&rhs != this)
  50.  {
  51.   if(rhs.X() == _iL && rhs.Y() == _iC)
  52.    for(int l = 0; l < _iL; ++l)
  53.     for(int c = 0; c < _iC; ++c)
  54.      _v[l * _iC + c] = rhs(l, c);
  55.   else return NULL;
  56.  }
  57.  return (*this);
  58. }
  59.    
  60.     /// @brief remplit la table avec la valeur val
  61.  inline int remplit(const T& val) {
  62.  int nbelem(_iL * _iC);
  63.  _v.assign(nbelem, val);
  64.  return nbelem;
  65. }
  66. /// @brief applique la fonction f(arg) aux éléments de la table     
  67. template<typename ret>
  68. void applique(ret (*f)(T)) {
  69.  typename vector<T>::iterator it = _v.begin();
  70.  while(it != _v.end()) {
  71.   *it = (*f)(*it);
  72.   ++it;
  73.  }
  74. }
  75.         /// @brief applique la fonction f(arg1, arg2) aux éléments de la table
  76.         /// arg2 doit être du type !!! exact !!! demandé par la fonction f, aucune conversion implicite n'étant possible
  77. template<typename ret, typename A>
  78. void applique(ret (*f)(T, A), A arg2) {
  79.  typename vector<T>::iterator it = _v.begin();
  80.  while(it != _v.end()) {
  81.   *it = (*f)(*it, arg2);
  82.   ++it;
  83.  }
  84. }
  85. //friend ostream& operator<<(ostream& os, Matrice<T>& mat) const {;}
  86. protected:
  87. int _iL, _iC; // lignes, colonnes
  88. vector<T> _v;      // notre structure d'accueil
  89. };
  90. #endif
 

Programme de test :

Code :
  1. #include <cmath>
  2. #include <iostream>
  3. #include <ostream>
  4. #include "Matrice.h"
  5. using namespace std;
  6. typedef Matrice<double> Matdbl;
  7. ostream& operator<<(ostream& os, Matdbl & mat) {
  8. int L = mat.X(), C = mat.Y();
  9. for(int l = 0; l < L; ++l) {
  10.  os << "[ ";
  11.  for(int c = 0; c < C; ++c)
  12.   os << mat(l, c) << '\t';
  13.  os << "]" << endl;
  14. }
  15.        return os;
  16. }
  17. double f1(double x){ return sqrt(fabs(x)); }
  18. double f2(double x, int i){ return (x * i); }
  19. int main(int argc, char* argv[])
  20. {
  21. cout << "Matrice d'origine\n" << endl;
  22. Matdbl M(7, 7);
  23. Matdbl N(7, 7);
  24. cout << "fill" << endl;//M;
  25. M.remplit(-1.);
  26. cout << "Divers acces en lecture/ecriture" << endl;
  27. for(short i = 1; i < M.X(); i++) M(i, 0) = i;
  28. for(short j = 1; j < M.Y(); j++) M(0, j) = j;
  29. for(short j = 0; j < M.Y(); j++) M(j, j) = 1.;
  30. cout << "Une recopie" << endl;
  31. N = M;
  32. cout << "M =\n" << M;
  33. cout << "N =\n" << N;
  34. M.applique(&f1);
  35. cout << "sqrt(fabs(elem)) = \n" << M;
  36. M.applique(&f2, 2);
  37. cout << "M x 2 = \n" << M;
  38. return 0;
  39. }

Message cité 1 fois
Message édité par el muchacho le 03-08-2010 à 08:26:46

---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 14-11-2005 à 18:13:10    

Reply

Marsh Posté le 14-11-2005 à 18:34:42    

si tu as qqs patiences, je peut te filer une beta de mon boulot sur une bibliotheque de matrice/algebre/geometry template avec des perfs egales a 0.95-1.2 celles du C

Reply

Marsh Posté le 14-11-2005 à 19:29:30    

Merci !
 
Je n'abandonne pas Delphi du tout mais là pour le coup j'ai pas le choix du language...

Reply

Marsh Posté le 14-11-2005 à 21:00:43    

el muchacho a écrit :

Quelle taille, tes matrices ? Quelle utilisation ?  
Voici un petit template maison pour des matrices jusqu'à, disons 500x500. Au delà, une vraie lib est nécessaire.


 
Tu penses que ta classe n'est pas utilisable pour des matrices supérieures à 500x500, ou qu'une vraie lib (boost::numeric::ublas par exemple) n'est pas nécessaire en dessous de 500x500 ?
 
 
 

Reply

Marsh Posté le 14-11-2005 à 21:24:43    

++fab a écrit :

Tu penses que ta classe n'est pas utilisable pour des matrices supérieures à 500x500, ou qu'une vraie lib (boost::numeric::ublas par exemple) n'est pas nécessaire en dessous de 500x500 ?


Un peu des deux. Disons que l'avantage principal de ma classe est qu'elle est immédiatement utilisable et facilement adaptable et on n'a pas besoin de lire la doc. Et accessoirement, elle marche et n'est pas (trop) buggée (utilisée dans un projet industriel en temps réel embarqué sur de petites matrices 50x50). Maintenant, elle n'est pas optimisée pour des calculs lourds sur de grosses matrices comme peut l'être uBlas ou la lib de Joel F, ni même pour faire du traitement d'image par ex. Ce n'est pas le but.


---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 14-11-2005 à 22:01:59    

el muchacho a écrit :

Un peu des deux. Disons que l'avantage principal de ma classe est qu'elle est immédiatement utilisable et facilement adaptable et on n'a pas besoin de lire la doc. Et accessoirement, elle marche et n'est pas (trop) buggée (utilisée dans un projet industriel en temps réel embarqué sur de petites matrices 50x50). Maintenant, elle n'est pas optimisée pour des calculs lourds sur de grosses matrices comme peut l'être uBlas ou la lib de Joel F, ni même pour faire du traitement d'image par ex. Ce n'est pas le but.


 
immédiatement utilisable ... pour une utilisation restreinte. si on veut résoudre un système linéaire (à tout hasard), ça me parait osé de se lancer sur la base d'une lib maison.
en survolant la doc, on se sert de ublas dans la demi-heure.
Je ne pense pas qu'il y ait une taille limite de matrice, en dessous de laquelle l'utilisation de ublas soit nuisible.

Reply

Marsh Posté le 14-11-2005 à 22:11:57    

Je n'ai jamais dit le contraire. Après, tout dépend de l'utilisation qu'on en fait, comme toujours. Pour l'appli pour laquelle j'ai écrit cette petite classe, par ex. il était hors de question d'utiliser Boost.


---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 14-11-2005 à 22:11:57   

Reply

Marsh Posté le 14-11-2005 à 22:35:48    

alors ton refus d'utiliser ublas n'etait pas lié à la taille des matrices :)
 

Citation :

Après, tout dépend de l'utilisation qu'on en fait,


on a pas avancé d'un pouce du coup  [:petrus75]

Reply

Marsh Posté le 15-11-2005 à 21:04:07    

++fab a écrit :

alors ton refus d'utiliser ublas n'etait pas lié à la taille des matrices :)
 

Citation :

Après, tout dépend de l'utilisation qu'on en fait,


on a pas avancé d'un pouce du coup  [:petrus75]


Ce n'est pas que je refuse d'utiliser uBlas. D'où tu sors ça ?  :sleep:  
De toute façon, des libs de calcul matriciel performantes, il y en a des tas, comme Blitz++ par ex.
Mais dans les contraintes que j'avais (de mémoire notamment)  et pour des matrices 30x30, c'est contre-productif de sortir la grosse artillerie, c'est tout. Et non, il n'y avait pas de système d'équations à résoudre ni de valeurs propres à calculer. Donc voilà, point. P-ê que Kyle Katarn est dans le même cas de figure ou qq chose de semblable (et pour des petites matrices, écrire un pivot de Gauss ou une décomposition LU n'est pas très compliqué non plus), et dans ce cas, ma classe est très suffisante. Il en fait ce qu'il en veut, je n'oblige personne à l'utiliser.

Message cité 1 fois
Message édité par el muchacho le 15-11-2005 à 21:18:02

---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 16-11-2005 à 00:17:07    

el muchacho a écrit :

Ce n'est pas que je refuse d'utiliser uBlas. D'où tu sors ça ?  :sleep:


je voulais dire que tu ne l'avais pas utilisée pour le cas que tu décris. :sleep:  
 

el muchacho a écrit :

Mais dans les contraintes que j'avais (de mémoire notamment)  et pour des matrices 30x30, c'est contre-productif de sortir la grosse artillerie, c'est tout.


Tu la sors gratuitement, ta limite  de contre-productivité (30x30 ce coup ci), ou tu as réellement mesuré un surcout de consommation memoire, une mauvaise performance, une mauvaise productivité, une dépendance en plus, ... auquel cas, ça m'intéresse, pas que je cherche la petite bete.

Reply

Marsh Posté le 16-11-2005 à 00:33:31    

Reply

Marsh Posté le 16-11-2005 à 00:39:36    

Si tu dis n'importe quoi, faut pas t'étonner ...

Reply

Marsh Posté le 16-11-2005 à 08:30:30    

Mon projet est un solveur sous contraintes, qui doit gérer des tables sous forme de matrice et leur coller des opérateurs SELECT, JOIN ...
 
Je vais démarrer avec la template citée plus haut et je verrai bien les perfs qu'elle me donne ...

Reply

Marsh Posté le 16-11-2005 à 13:26:19    

++fab a écrit :

Si tu dis n'importe quoi, faut pas t'étonner ...


Mais bien sûr, M. l'Expert... :sarcastic:  :sarcastic:


---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 16-11-2005 à 19:46:46    

bref, je pense que tu as tort sur ce coup, je te demande une explication, tu m'envoies paitre, tu m'insulte, et tu ironises. bye.

Reply

Marsh Posté le 16-11-2005 à 21:34:31    

Oui je t'envoie paître parce que tu ne demandes pas une explication, - je t'en ai déjà donnée -, tu te la joues Grand Inquisiteur possédant LA connaissance du C++.  
Alors je te la faire longue : quand tu fais de l'embarqué dans un calculateur militaire, automobile ou dans un téléphone portable, d'une, tu ne fous pas impunément n'importe quelle lib dans ton code pour calculer 3 matrices 30x30, de deux, le code doit pouvoir être contrôlable, surtout si tu compares ce code à un original existant en Fortran, ce qui te promet de belles nuits de bonheur si tu le fais avec uBlas, parce que ton chef ou ton collègue ne va pas relire le code de Boost pour ces 3 malheureuses matrices, ok ?? (et je me fous royalement de ton avis sur Boost n'étant pas "n'importe quelle lib" ), trois, comme ce genre de libs sont fortement templatisés, il y a de bonnes chances que ton code explose, ce que tu tiens parfois à éviter, quatre, parce que tu ne choisis pas forcément ton compilo, cinq parce que les perfs étaient de toute façon cinq ou dix fois supérieures aux exigences. Je suis sûr que je peux trouver d'autres raisons mais ça suffira. Voilà. Quand tu auras quelques notions d'industrialisation du code tu pourras venir donner tes leçons. En attendant merci de me lâcher la grappe...

Message cité 1 fois
Message édité par el muchacho le 16-11-2005 à 21:42:55

---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le 16-11-2005 à 21:37:51    

J'en demandais pas tant, ne vous emportez pas non plus ... ;-)

Reply

Marsh Posté le 16-11-2005 à 22:09:07    

el muchacho a écrit :

Oui je t'envoie paître parce que tu ne demandes pas une explication, - je t'en ai déjà donnée -, tu te la joues Grand Inquisiteur possédant LA connaissance du C++.  
Alors je te la faire longue : quand tu fais de l'embarqué dans un calculateur militaire, automobile ou dans un téléphone portable, d'une, tu ne fous pas impunément n'importe quelle lib dans ton code pour calculer 3 matrices 30x30, de deux, le code doit pouvoir être contrôlable, surtout si tu compares ce code à un original existant en Fortran, ce qui te promet de belles nuits de bonheur si tu le fais avec uBlas, parce que ton chef ou ton collègue ne va pas relire le code de Boost pour ces 3 malheureuses matrices, ok ?? (et je me fous royalement de ton avis sur Boost n'étant pas "n'importe quelle lib" ), trois, comme ce genre de libs sont fortement templatisés, il y a de bonnes chances que ton code explose, ce que tu tiens parfois à éviter, quatre, parce que tu ne choisis pas forcément ton compilo, cinq parce que les perfs étaient de toute façon cinq ou dix fois supérieures aux exigences. Je suis sûr que je peux trouver d'autres raisons mais ça suffira. Voilà. Quand tu auras quelques notions d'industrialisation du code tu pourras venir donner tes leçons. En attendant merci de me lâcher la grappe...


 
merci pour ce pur moment d'anthologie. Apparemment, tu ne lis pas mes posts, ou tu ne fais pas l'effort de les comprendre. La preuve, tu n'as toujours compris ce que j'essayais de te dire. J'abandonne, mais je me fendrai la gueule de te relire. bo

Reply

Marsh Posté le 16-11-2005 à 22:10:19    

J'en demandais pas tant, ne vous emportez pas non plus ... ;-)

Reply

Marsh Posté le 16-11-2005 à 23:10:39    

++fab a écrit :

merci pour ce pur moment d'anthologie. Apparemment, tu ne lis pas mes posts, ou tu ne fais pas l'effort de les comprendre. La preuve, tu n'as toujours compris ce que j'essayais de te dire.


A quoi bon ? Il n'y a rien dedans. :sleep:


---------------
Les aéroports où il fait bon attendre, voila un topic qu'il est bien
Reply

Marsh Posté le    

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed