MAGiC  V5.0
Mailleurs Automatiques de Géometries intégrés à la Cao
mailleur3d_optimisation.cpp
Aller à la documentation de ce fichier.
1 //####//------------------------------------------------------------
2 //####//------------------------------------------------------------
3 //####// MAGiC
4 //####// Jean Christophe Cuilliere et Vincent FRANCOIS
5 //####// Departement de Genie Mecanique - UQTR
6 //####//------------------------------------------------------------
7 //####// MAGIC est un projet de recherche de l equipe ERICCA
8 //####// du departement de genie mecanique de l Universite du Quebec a Trois Rivieres
9 //####// http://www.uqtr.ca/ericca
10 //####// http://www.uqtr.ca/
11 //####//------------------------------------------------------------
12 //####//------------------------------------------------------------
13 //####//
14 //####// mailleur3d_optimisation.cpp
15 //####//
16 //####//------------------------------------------------------------
17 //####//------------------------------------------------------------
18 //####// COPYRIGHT 2000-2024
19 //####// jeu 13 jun 2024 11:58:55 EDT
20 //####//------------------------------------------------------------
21 //####//------------------------------------------------------------
22 
23 
24 #include "gestionversion.h"
26 #include "ot_mathematique.h"
27 #include "m3d_tetra.h"
28 #include "m3d_triangle.h"
29 #include "m3d_noeud.h"
30 #include "mg_maillage.h"
31 #include <math.h>
32 
33 
34 
35 
36 MAILLEUR3D_OPTIMISATION::MAILLEUR3D_OPTIMISATION(MG_MAILLAGE* mgmai,int niv):MAILLEUR(false),mg_maillage(mgmai),niveau_optimisation(niv)
37 {
38 o3d_data();
39 o3d_data2();
40 LISTE_MG_TETRA::iterator it;
42 for (MG_TETRA* tet=mg_maillage->get_premier_tetra(it);tet!=NULL;tet=mg_maillage->get_suivant_tetra(it))
43  if (tet->get_type_entite()!=MAGIC::TYPE_ENTITE::IDM3D_TETRA)
44  {
45  M3D_TETRA* tet3d=new M3D_TETRA(tet->get_id(),tet->get_lien_topologie(),tet->get_noeud1(),tet->get_noeud2(),tet->get_noeud3(),tet->get_noeud4(),tet->get_triangle1(),tet->get_triangle2(),tet->get_triangle3(),tet->get_triangle4(),tet->get_origine());
46  listetet3d.ajouter(tet3d);
47  }
48 
50 
51 for (M3D_TETRA* tet=listetet3d.get_premier(it2);tet!=NULL;tet=listetet3d.get_suivant(it2))
52  {
53  mg_maillage->supprimer_mg_tetraid(tet->get_id());
55  }
56 }
57 
59 {
60 }
61 
62 
63 
65 {
66  double *xyz1=tet->get_noeud1()->get_coord();
67  double *xyz2=tet->get_noeud2()->get_coord();
68  double *xyz3=tet->get_noeud3()->get_coord();
69  double *xyz4=tet->get_noeud4()->get_coord();
70  OT_VECTEUR_3D ab(xyz1,xyz2);
71  OT_VECTEUR_3D ac(xyz1,xyz3);
72  OT_VECTEUR_3D ad(xyz1,xyz4);
73  double vol=(ab&ac)*ad;
74  vol=vol/6.;
75  return vol;
76 }
77 
78 double MAILLEUR3D_OPTIMISATION::get_volume(double *xyz1,double *xyz2,double *xyz3,double *xyz4)
79 {
80  OT_VECTEUR_3D ab(xyz1,xyz2);
81  OT_VECTEUR_3D ac(xyz1,xyz3);
82  OT_VECTEUR_3D ad(xyz1,xyz4);
83  double vol=(ab&ac)*ad;
84  vol=vol/6.;
85  return vol;
86 }
87 
89 {
90  char mess[255];
91  sprintf(mess," Niveau d'optimisation : %d",niveau_optimisation);
92  if (affichageactif==1) affiche(mess);
93  int nbaoptimiser;
94  int nbaoptimiserapres=mg_maillage->get_nb_mg_tetra();
95  do
96  {
97  nbaoptimiser=nbaoptimiserapres;
98  optimise(mgvol,nbaoptimiserapres);
99  if (nbaoptimiserapres==0)
100  {
101  nbaoptimiser=0;
102  sprintf(mess," Tout est optimise");
103  if (affichageactif==1) affiche(mess);
104  }
105 
106  }
107  while (nbaoptimiserapres!=nbaoptimiser);
108 }
109 
110 
111 
112 void MAILLEUR3D_OPTIMISATION::optimise(MG_VOLUME* mgvol,int& nbmauvais)
113 {
114  int passe=1;
115  //passe++;
116  int nbtet=0;
117  if (mgvol!=NULL)
118  {
120  for (MG_TETRA* tet=(MG_TETRA*)mgvol->get_lien_maillage()->get_premier(it);tet;tet=(MG_TETRA*)mgvol->get_lien_maillage()->get_suivant(it))
121  {
122  if (mg_maillage->get_mg_tetraid(tet->get_id())==NULL) continue;
123  M3D_TETRA* mtet=(M3D_TETRA*)tet;
124  double qual=OPERATEUR::qualite_tetra(mtet->get_noeud1()->get_coord(),mtet->get_noeud2()->get_coord(),mtet->get_noeud3()->get_coord(),mtet->get_noeud4()->get_coord());
125  mtet->change_qualite(qual);
126  if (qual<0.1*niveau_optimisation) nbtet++;
127  ajouter_ordre_tetra(mtet,0);
128  }
129  }
130  else
131  {
132  LISTE_MG_TETRA::iterator it;
134  {
135  if (mg_maillage->get_mg_tetraid(tet->get_id())==NULL) continue;
136  M3D_TETRA* mtet=(M3D_TETRA*)tet;
137  double qual=OPERATEUR::qualite_tetra(mtet->get_noeud1()->get_coord(),mtet->get_noeud2()->get_coord(),mtet->get_noeud3()->get_coord(),mtet->get_noeud4()->get_coord());
138  mtet->change_qualite(qual);
139  if (qual<0.1*niveau_optimisation) nbtet++;
140  ajouter_ordre_tetra(mtet,0);
141  }
142  }
143 
144  if (nbtet==0) return;
145  for (int phase=0;phase<2;phase++)
146  {
147  char mess[255];
148  if (phase==0) sprintf(mess," Phase %d : %d a optimiser",2*passe-1+phase,nbtet);
149  if (phase==1) sprintf(mess," Phase %d",2*passe-1+phase);
150  if (affichageactif==1) affiche(mess);
151  while (lst_tetra[phase].size()>0)
152  {
153  ORDRE_TETRA::iterator i=lst_tetra[phase].begin();
154  M3D_TETRA* tet=(*i).second;
156  double crit_avant=tet->get_qualite();
157  if (crit_avant<0.1*niveau_optimisation)
158  {
159  double crit[4]={-1.,-1.,-1.,-1.};
160  MG_NOEUD* no[4];
161  no[0]=(MG_NOEUD*)tet->get_noeud1();
162  no[1]=(MG_NOEUD*)tet->get_noeud2();
163  no[2]=(MG_NOEUD*)tet->get_noeud3();
164  no[3]=(MG_NOEUD*)tet->get_noeud4();
165  double x[4],y[4],z[4];
166  bouge_point(mgvol,no[0],crit[0],x[0],y[0],z[0]);
167  bouge_point(mgvol,no[1],crit[1],x[1],y[1],z[1]);
168  bouge_point(mgvol,no[2],crit[2],x[2],y[2],z[2]);
169  bouge_point(mgvol,no[3],crit[3],x[3],y[3],z[3]);
170  std::vector<double> vecteur_crit(crit,crit+4);
171  std::vector<double>::iterator it1 = max_element(vecteur_crit.begin(), vecteur_crit.end());
172  double crit_opt=*it1;
173  if (crit_opt>crit_avant)
174  {
175  int num=it1-vecteur_crit.begin();
176  no[num]->change_x(x[num]);
177  no[num]->change_y(y[num]);
178  no[num]->change_z(z[num]);
179  int nb=no[num]->get_lien_tetra()->get_nb();
180  for (int j=0;j<nb;j++)
181  {
182  M3D_TETRA* mtet=(M3D_TETRA*)no[num]->get_lien_tetra()->get(j);
183  double qual=OPERATEUR::qualite_tetra(mtet->get_noeud1()->get_coord(),mtet->get_noeud2()->get_coord(),mtet->get_noeud3()->get_coord(),mtet->get_noeud4()->get_coord());
184  mtet->change_qualite(qual);
185  }
186  crit_avant=crit_opt;
187  }
188  }
189 
190  int coquille_non_optimise=1;
191  if (crit_avant<0.1*niveau_optimisation)
192  {
193  COQUILLE coque[6];
194  double crit[6]={-1,-1,-1,-1,-1,-1};
195  remaille_coquille(tet->get_noeud1(),tet->get_noeud2(),crit[0],coque[0]);
196  remaille_coquille(tet->get_noeud1(),tet->get_noeud3(),crit[1],coque[1]);
197  remaille_coquille(tet->get_noeud1(),tet->get_noeud4(),crit[2],coque[2]);
198  remaille_coquille(tet->get_noeud2(),tet->get_noeud3(),crit[3],coque[3]);
199  remaille_coquille(tet->get_noeud2(),tet->get_noeud3(),crit[4],coque[4]);
200  remaille_coquille(tet->get_noeud3(),tet->get_noeud4(),crit[5],coque[5]);
201  std::vector<double> vecteur_crit(crit,crit+6);
202  std::vector<double>::iterator it1 = max_element(vecteur_crit.begin(), vecteur_crit.end());
203  double crit_opt=*it1;
204  if (crit_opt>crit_avant)
205  {
206  coquille_non_optimise=0;
207  int num=it1-vecteur_crit.begin();
208  for (int i=0;i<coque[num].taille;i++)
209  {
210  M3D_TETRA *tettmp=(M3D_TETRA*)coque[num].tet[i];
211  if (tet!=tettmp) supprimer_ordre_tetra(tettmp);
212  mg_maillage->supprimer_mg_tetraid(coque[num].tet[i]->get_id());
213  }
214  for (int i=0;i<2*coque[num].taille-4;i++)
215  {
216  MG_NOEUD* noeud1=coque[num].new_tetra[4*i];
217  MG_NOEUD* noeud2=coque[num].new_tetra[4*i+1];
218  MG_NOEUD* noeud3=coque[num].new_tetra[4*i+2];
219  MG_NOEUD* noeud4=coque[num].new_tetra[4*i+3];
220  MG_TRIANGLE* triangle1=mg_maillage->get_mg_triangle(noeud1->get_id(),noeud3->get_id(),noeud2->get_id());
221  MG_TRIANGLE* triangle2=mg_maillage->get_mg_triangle(noeud1->get_id(),noeud2->get_id(),noeud4->get_id());
222  MG_TRIANGLE* triangle3=mg_maillage->get_mg_triangle(noeud2->get_id(),noeud3->get_id(),noeud4->get_id());
223  MG_TRIANGLE* triangle4=mg_maillage->get_mg_triangle(noeud1->get_id(),noeud4->get_id(),noeud3->get_id());
224  if (triangle1==NULL) triangle1=insere_triangle(mgvol,noeud1,noeud3,noeud2,MAGIC::ORIGINE::MAILLEUR_AUTO);
225  if (triangle2==NULL) triangle2=insere_triangle(mgvol,noeud1,noeud2,noeud4,MAGIC::ORIGINE::MAILLEUR_AUTO);
226  if (triangle3==NULL) triangle3=insere_triangle(mgvol,noeud2,noeud3,noeud4,MAGIC::ORIGINE::MAILLEUR_AUTO);
227  if (triangle4==NULL) triangle4=insere_triangle(mgvol,noeud1,noeud4,noeud3,MAGIC::ORIGINE::MAILLEUR_AUTO);
228  M3D_TETRA* mtet=new M3D_TETRA(mgvol,noeud1,noeud2,noeud3,noeud4,triangle1,triangle2,triangle3,triangle4,MAGIC::ORIGINE::MAILLEUR_AUTO);
230  double qual=OPERATEUR::qualite_tetra(mtet->get_noeud1()->get_coord(),mtet->get_noeud2()->get_coord(),mtet->get_noeud3()->get_coord(),mtet->get_noeud4()->get_coord());
231  mtet->change_qualite(qual);
232  if (phase==0)
233  ajouter_ordre_tetra(mtet,1);
234  }
235 
236 
237  }
238 
239  }
240  if ((phase==0) && (coquille_non_optimise==1))
241  ajouter_ordre_tetra(tet,1);
242  }
243 
244  }
245  int nb=0;
246  //for (MG_TETRA* tet=mg_maillage->get_premier_tetra(it);tet;tet=mg_maillage->get_suivant_tetra(it))
247  if (mgvol!=NULL)
248  {
250  for (MG_TETRA* tet=(MG_TETRA*)mgvol->get_lien_maillage()->get_premier(it);tet;tet=(MG_TETRA*)mgvol->get_lien_maillage()->get_suivant(it))
251  {
252  if (mg_maillage->get_mg_tetraid(tet->get_id())==NULL) continue;
253  M3D_TETRA* mtet=(M3D_TETRA*)tet;
254  if (mtet->get_qualite()<0.1*niveau_optimisation) nb++;
255  }
256  }
257  else
258  {
259  LISTE_MG_TETRA::iterator it;
261  {
262  if (mg_maillage->get_mg_tetraid(tet->get_id())==NULL) continue;
263  M3D_TETRA* mtet=(M3D_TETRA*)tet;
264  if (mtet->get_qualite()<0.1*niveau_optimisation) nb++;
265  }
266  }
267 
268  nbmauvais=nb;
269 
270 }
271 
272 
273 
274 int MAILLEUR3D_OPTIMISATION::bouge_point(MG_VOLUME* mgvol,MG_NOEUD* noeud,double& crit,double& x,double& y, double& z)
275 {
276  if (noeud->get_origine()!=MAGIC::ORIGINE::MAILLEUR_AUTO) return 0;
277  // if (noeud->get_type_entite()!=IDM3D_NOEUD) return 0;
278 
279  if (mgvol!=NULL)
280  if (noeud->get_lien_topologie()!=mgvol) return 0;
281  if (mgvol==NULL)
283  if (((M3D_NOEUD*)noeud)->get_etat()==MAGIC::MAILLEURFRONTALETAT::INACTIF) return 0;
284  double xopt=0.;
285  double yopt=0.;
286  double zopt=0.;
287  double qual_dep=1.;
288  int nb_tet=noeud->get_lien_tetra()->get_nb();
289  double tab_coord[3000];
290  double gamma=0;
291  for (int i=0;i<nb_tet;i++)
292  {
293  M3D_TETRA* tet=(M3D_TETRA*)noeud->get_lien_tetra()->get(i);
294  qual_dep=std::min(qual_dep,tet->get_qualite());
295  MG_NOEUD* no1=tet->get_noeud1();
296  MG_NOEUD* no2=tet->get_noeud2();
297  MG_NOEUD* no3=tet->get_noeud3();
298  MG_NOEUD* no4=tet->get_noeud4();
299  MG_NOEUD *noeud1,*noeud2,*noeud3;
300  if (no1==noeud)
301  {
302  noeud1=no2;
303  noeud2=no4;
304  noeud3=no3;
305  }
306  if (no2==noeud)
307  {
308  noeud1=no1;
309  noeud2=no3;
310  noeud3=no4;
311  }
312  if (no3==noeud)
313  {
314  noeud1=no1;
315  noeud2=no4;
316  noeud3=no2;
317  }
318  if (no4==noeud)
319  {
320 
321  noeud1=no1;
322  noeud2=no2;
323  noeud3=no3;
324  }
325  double xyzi[3];
326  double *xyz1=noeud1->get_coord();
327  double *xyz2=noeud2->get_coord();
328  double *xyz3=noeud3->get_coord();
329  xyzi[0]=(xyz1[0]+xyz2[0]+xyz3[0])/3.;
330  xyzi[1]=(xyz1[1]+xyz2[1]+xyz3[1])/3.;
331  xyzi[2]=(xyz1[2]+xyz2[2]+xyz3[2])/3.;
332  OT_VECTEUR_3D v12(xyz1,xyz2);
333  OT_VECTEUR_3D v13(xyz1,xyz3);
334  OT_VECTEUR_3D v23(xyz2,xyz3);
335  OT_VECTEUR_3D normal=v12&v13;
336  double perimetre=v12.get_longueur()+v13.get_longueur()+v23.get_longueur();
337  double hauteur = (perimetre/3.) * 0.8 ;
338  normal.norme();
339  tab_coord[3*i]=xyzi[0]+normal.get_x()*hauteur;
340  tab_coord[3*i+1]=xyzi[1]+normal.get_y()*hauteur;
341  tab_coord[3*i+2]=xyzi[2]+normal.get_z()*hauteur;
342  if (tet->get_qualite()> 1e-10) gamma=gamma+1./tet->get_qualite()/tet->get_qualite();
343  }
344  gamma=1./gamma;
345  for (int i=0;i<nb_tet;i++)
346  {
347  M3D_TETRA* tet=(M3D_TETRA*)noeud->get_lien_tetra()->get(i);
348  if (tet->get_qualite()> 1e-10)
349  {
350  double alpha=gamma/tet->get_qualite()/tet->get_qualite();
351  xopt=xopt+alpha*tab_coord[3*i];
352  yopt=yopt+alpha*tab_coord[3*i+1];
353  zopt=zopt+alpha*tab_coord[3*i+2];
354  }
355 
356  }
357  double delta[3]={xopt-noeud->get_x(),yopt-noeud->get_y(),zopt-noeud->get_z()};
358  double bmin=0.,bmax=1.;
359  double vieuxx=noeud->get_x();
360  double vieuxy=noeud->get_y();
361  double vieuxz=noeud->get_z();
362  double qualini=0.;
363  for (int iteration=0;iteration<5;iteration++)
364  {
365  double alpha=(bmin+bmax)*0.5;
366  noeud->change_x(vieuxx+alpha*delta[0]);
367  noeud->change_y(vieuxy+alpha*delta[1]);
368  noeud->change_z(vieuxz+alpha*delta[2]);
369  double qualcour=1.;
370  for (int i=0;i<nb_tet;i++)
371  {
372  M3D_TETRA* mtet=(M3D_TETRA*)noeud->get_lien_tetra()->get(i);
373  double qual=OPERATEUR::qualite_tetra(mtet->get_noeud1()->get_coord(),mtet->get_noeud2()->get_coord(),mtet->get_noeud3()->get_coord(),mtet->get_noeud4()->get_coord());
374  qualcour=std::min(qualcour,qual);
375  }
376  double alpha_eps=(bmin+bmax)*0.5-(bmax-bmin)/50.;
377  noeud->change_x(vieuxx+alpha_eps*delta[0]);
378  noeud->change_y(vieuxy+alpha_eps*delta[1]);
379  noeud->change_z(vieuxz+alpha_eps*delta[2]);
380  double qualcour_eps=1.;
381  for (int i=0;i<nb_tet;i++)
382  {
383  M3D_TETRA* mtet=(M3D_TETRA*)noeud->get_lien_tetra()->get(i);
384  double qual=OPERATEUR::qualite_tetra(mtet->get_noeud1()->get_coord(),mtet->get_noeud2()->get_coord(),mtet->get_noeud3()->get_coord(),mtet->get_noeud4()->get_coord());
385  qualcour_eps=std::min(qualcour_eps,qual);
386  }
387  if (qualcour>qualcour_eps) bmin =alpha;
388  else bmax=alpha;
389  qualini=std::max(qualini,qualcour);
390  }
391  noeud->change_x(vieuxx);
392  noeud->change_y(vieuxy);
393  noeud->change_z(vieuxz);
394  if (qualini>qual_dep)
395  {
396  x=vieuxx+(bmin+bmax)*0.5*delta[0];
397  y=vieuxy+(bmin+bmax)*0.5*delta[1];
398  z=vieuxz+(bmin+bmax)*0.5*delta[2];
399  crit=qualini;
400  return 1;
401  }
402 
403  return 0;
404 }
405 
406 
407 
408 void MAILLEUR3D_OPTIMISATION::remaille_coquille(MG_NOEUD* noeud1,MG_NOEUD* noeud2, double& crit, COQUILLE& coque)
409 {
410  MG_NOEUD* noeud;
411  if (noeud1->get_id()>noeud2->get_id()) noeud=noeud2;
412  else noeud=noeud1;
413  int nb=noeud->get_lien_petit_segment()->get_nb();
414  for (int i=0;i<nb;i++)
415  {
416  MG_SEGMENT* seg=noeud->get_lien_petit_segment()->get(i);
417  if ( ((seg->get_noeud1()==noeud1) && (seg->get_noeud2()==noeud2)) || ((seg->get_noeud1()==noeud2) && (seg->get_noeud2()==noeud1)))
418  {
419  //if (mg_maillage->get_mg_geometrie()==NULL)
420  //{
421  if (seg->get_dimension_topo_null()==2)
422  {
423  coque.taille=0;
424  crit=0.;
425  return;
426  }
427  //}
428  //else
429  if (seg->get_lien_topologie()!=NULL) if ((seg->get_lien_topologie()->get_dimension()!=3) || (seg->get_origine()!=MAGIC::ORIGINE::MAILLEUR_AUTO))
430  {
431  coque.taille=0;
432  crit=0.;
433  return;
434  }
435  }
436  }
437  int nb1=noeud1->get_lien_tetra()->get_nb();
438  int nb2=noeud2->get_lien_tetra()->get_nb();
439  MG_TETRA* coq[100];
440  int nb_coq=0;
441  for (int i=0;i<nb1;i++)
442  for (int j=0;j<nb2;j++)
443  if (noeud1->get_lien_tetra()->get(i)==noeud2->get_lien_tetra()->get(j))
444  {
445  coq[nb_coq]=noeud1->get_lien_tetra()->get(i);
446  nb_coq++;
447  }
448  if ((nb_coq<4) || (nb_coq>10))
449  {
450  coque.taille=0;
451  crit=0.;
452  return;
453  }
454  MG_NOEUD* tet_noeud[50];
455  int nb_tet_noeud=0;
456  coque.taille=nb_coq;
457  for (int i=0;i<nb_coq;i++)
458  {
459  coque.tet[i]=coq[i];
460 
461  if ((coq[i]->get_noeud1()!=noeud1) && (coq[i]->get_noeud1()!=noeud2)) tet_noeud[nb_tet_noeud++]=coq[i]->get_noeud1();
462  if ((coq[i]->get_noeud2()!=noeud1) && (coq[i]->get_noeud2()!=noeud2)) tet_noeud[nb_tet_noeud++]=coq[i]->get_noeud2();
463  if ((coq[i]->get_noeud3()!=noeud1) && (coq[i]->get_noeud3()!=noeud2)) tet_noeud[nb_tet_noeud++]=coq[i]->get_noeud3();
464  if ((coq[i]->get_noeud4()!=noeud1) && (coq[i]->get_noeud4()!=noeud2)) tet_noeud[nb_tet_noeud++]=coq[i]->get_noeud4();
465  coque.volume=coque.volume+fabs(get_volume(coq[i]));
466  }
467  MG_NOEUD* polygone[20];
468  int nb_poly=2;
469  polygone[0]=tet_noeud[0];
470  tet_noeud[0]=NULL;
471  polygone[1]=tet_noeud[1];
472  tet_noeud[1]=NULL;
473  while (nb_poly!=nb_coq+1)
474  {
475  for (int j=0;j<nb_coq;j++)
476  {
477  if (tet_noeud[2*j]==polygone[nb_poly-1])
478  {
479  polygone[nb_poly++]=tet_noeud[2*j+1];
480  tet_noeud[2*j]=NULL;
481  tet_noeud[2*j+1]=NULL;
482  }
483  if (tet_noeud[2*j+1]==polygone[nb_poly-1])
484  {
485  polygone[nb_poly++]=tet_noeud[2*j];
486  tet_noeud[2*j]=NULL;
487  tet_noeud[2*j+1]=NULL;
488  }
489 
490  }
491  }
492  double vol1=get_volume(polygone[0]->get_coord(),polygone[1]->get_coord(),polygone[nb_poly-1]->get_coord(),noeud1->get_coord());
493  double vol2=get_volume(polygone[0]->get_coord(),polygone[nb_poly-1]->get_coord(),polygone[1]->get_coord(),noeud2->get_coord());
494  if (vol1*vol2<0.)
495  {
496  crit=0.;
497  coque.taille=0;
498  return;
499  }
500  MG_NOEUD *noeuda=noeud1;
501  MG_NOEUD *noeudb=noeud2;
502  if (vol1<0.)
503  {
504  noeuda=noeud2;
505  noeudb=noeud1;
506  }
507  int nb_solution,nb_triangle;
508 
509  if (nb_coq==4) {
510  nb_solution=2;
511  nb_triangle=4;
512  }
513  if (nb_coq==5) {
514  nb_solution=5;
515  nb_triangle=10;
516  }
517  if (nb_coq==6) {
518  nb_solution=14;
519  nb_triangle=20;
520  }
521  if (nb_coq==7) {
522  nb_solution=42;
523  nb_triangle=35;
524  }
525  if (nb_coq==8) {
526  nb_solution=132;
527  nb_triangle=56;
528  }
529  if (nb_coq==9) {
530  nb_solution=429;
531  nb_triangle=84;
532  }
533  if (nb_coq==10) {
534  nb_solution=1430;
535  nb_triangle=120;
536  }
537  double crit_triangle[120];
538  for (int i=0;i<nb_triangle;i++)
539  {
540  double crit1=OPERATEUR::qualite_tetra(polygone[tab_face[nb_coq-4][i][0]]->get_coord(),polygone[tab_face[nb_coq-4][i][1]]->get_coord(),polygone[tab_face[nb_coq-4][i][2]]->get_coord(),noeuda->get_coord());
541  double crit2=OPERATEUR::qualite_tetra(polygone[tab_face[nb_coq-4][i][0]]->get_coord(),polygone[tab_face[nb_coq-4][i][2]]->get_coord(),polygone[tab_face[nb_coq-4][i][1]]->get_coord(),noeudb->get_coord());
542  crit_triangle[i]=std::min(crit1,crit2);
543  }
544  /* examen de chaque solution */
545  double crit_opt=0.;
546  int numero_solution= -1;
547  double crit_solution[1430];
548  for (int i=0;i<nb_solution;i++)
549  {
550  double volume=0.;
551  for (int j=0;j<nb_coq-2;j++)
552  {
553  MG_NOEUD* noa=polygone[tab_face[nb_coq-4][tab_solution[nb_coq-4][i][j]][0]];
554  MG_NOEUD* nob=polygone[tab_face[nb_coq-4][tab_solution[nb_coq-4][i][j]][1]];
555  MG_NOEUD* noc=polygone[tab_face[nb_coq-4][tab_solution[nb_coq-4][i][j]][2]];
556  MG_NOEUD* nod=noeuda;
557  volume=volume+fabs(get_volume(noa->get_coord(),nob->get_coord(),noc->get_coord(),nod->get_coord()));
558  nod=noeudb;
559  volume=volume+fabs(get_volume(noa->get_coord(),nob->get_coord(),noc->get_coord(),nod->get_coord()));
560  }
561  double eps=0.0018*pow(volume,0.666666666);
562  if (OPERATEUR::egal(volume,coque.volume,eps))
563  {
564  crit_solution[i]=1.;
565  for (int j=0;j<nb_coq-2;j++)
566  crit_solution[i]=std::min(crit_solution[i],crit_triangle[tab_solution[nb_coq-4][i][j]]);
567  }
568  else crit_solution[i]=0.;
569  if (crit_opt<crit_solution[i])
570  {
571  crit_opt=crit_solution[i];
572  numero_solution=i;
573  }
574 
575  }
576  if (numero_solution==(-1))
577  {
578  crit=0.;
579  coque.taille=0;
580  return;
581  }
582  crit=crit_opt;
583  for (int j=0;j<nb_coq-2;j++)
584  {
585  MG_NOEUD* noa=polygone[tab_face[nb_coq-4][tab_solution[nb_coq-4][numero_solution][j]][0]];
586  MG_NOEUD* nob=polygone[tab_face[nb_coq-4][tab_solution[nb_coq-4][numero_solution][j]][1]];
587  MG_NOEUD* noc=polygone[tab_face[nb_coq-4][tab_solution[nb_coq-4][numero_solution][j]][2]];
588  coque.new_tetra[8*j]=noa;
589  coque.new_tetra[8*j+1]=nob;
590  coque.new_tetra[8*j+2]=noc;
591  coque.new_tetra[8*j+3]=noeuda;
592  coque.new_tetra[8*j+4]=noa;
593  coque.new_tetra[8*j+5]=noc;
594  coque.new_tetra[8*j+6]=nob;
595  coque.new_tetra[8*j+7]=noeudb;
596  }
597 }
598 
599 
601 {
602  double val;
603  if (num==0) val=tet->get_qualite();
604  if (num==1) val=1./tet->get_qualite();
605  std::pair<double,M3D_TETRA*> tmp(val,tet);
606  ORDRE_TETRA::iterator p=lst_tetra[num].insert(tmp);
607  lst_tetraid[num][tet->get_id()]=p;
608 }
609 
611 {
612  int num=0;
613  ORDRE_TETRA_PARID::iterator it=lst_tetraid[num].find(tet->get_id());
614  if (it==lst_tetraid[num].end())
615  {
616  num=1;
617  it=lst_tetraid[num].find(tet->get_id());
618  }
619  if (it==lst_tetraid[num].end()) return;
620  lst_tetra[num].erase(it->second);
621  lst_tetraid[num].erase(it);
622 }
623 
624 
626 {
628 }
629 
631 {
632  return niveau_optimisation;
633 }
634 
635 
636 
638 {
640  if (triangle!=NULL) return NULL;
644  if (segment1==NULL) segment1=cree_segment(mgvol,noeud1,noeud2,origine);
645  if (segment2==NULL) segment2=cree_segment(mgvol,noeud1,noeud3,origine);
646  if (segment3==NULL) segment3=cree_segment(mgvol,noeud2,noeud3,origine);
648  return tri;
649 }
650 
651 
652 
653 
654 
655 
657 {
660  return tri;
661 }
662 
663 
664 
666 {
669  return seg;
670 }
MG_MAILLAGE::ajouter_mg_tetra
MG_TETRA * ajouter_mg_tetra(MG_ELEMENT_TOPOLOGIQUE *topo, class MG_NOEUD *mgnoeud1, class MG_NOEUD *mgnoeud2, class MG_NOEUD *mgnoeud3, class MG_NOEUD *mgnoeud4, int origine, unsigned long num=0)
Definition: mg_maillage.cpp:1158
MAILLEUR3D_OPTIMISATION::cree_segment
virtual MG_SEGMENT * cree_segment(class MG_VOLUME *mgvol, MG_NOEUD *noeud1, MG_NOEUD *noeud2, int origine)
Definition: mailleur3d_optimisation.cpp:665
TPL_MAP_ENTITE::get_premier
virtual X get_premier(ITERATEUR &it)
Definition: tpl_map_entite.h:112
MG_SEGMENT
Definition: mg_segment.h:38
M3D_NOEUD
Definition: m3d_noeud.h:32
MAGIC::TYPE_ENTITE::IDM3D_TETRA
@ IDM3D_TETRA
Definition: mg_definition.h:69
COQUILLE::taille
int taille
Definition: mailleur3d_optimisation.h:92
MG_TETRA::get_noeud2
virtual MG_NOEUD * get_noeud2(void)
Definition: mg_tetra.cpp:148
gestionversion.h
MG_MAILLAGE::ajouter_mg_segment
MG_SEGMENT * ajouter_mg_segment(MG_ELEMENT_TOPOLOGIQUE *topo, class MG_NOEUD *mgnoeud1, class MG_NOEUD *mgnoeud2, int origine, double longue=0.0, unsigned long num=0)
Definition: mg_maillage.cpp:565
TPL_MAP_ENTITE
Definition: tpl_map_entite.h:35
MAILLEUR3D_OPTIMISATION::insere_triangle
virtual class MG_TRIANGLE * insere_triangle(class MG_VOLUME *mgvol, MG_NOEUD *noeud1, MG_NOEUD *noeud2, MG_NOEUD *noeud3, int origine)
Definition: mailleur3d_optimisation.cpp:637
MAILLEUR3D_OPTIMISATION::mg_maillage
MG_MAILLAGE * mg_maillage
Definition: mailleur3d_optimisation.h:78
MG_SEGMENT::get_noeud2
virtual MG_NOEUD * get_noeud2(void)
Definition: mg_segment.cpp:113
MG_NOEUD::get_z
virtual double get_z(void)
Definition: mg_noeud.cpp:87
MAILLEUR3D_OPTIMISATION::ajouter_ordre_tetra
virtual void ajouter_ordre_tetra(M3D_TETRA *tet, int num=1)
Definition: mailleur3d_optimisation.cpp:600
MG_IDENTIFICATEUR::get_id
unsigned long get_id()
Definition: mg_identificateur.cpp:53
MG_TETRA::get_noeud1
virtual MG_NOEUD * get_noeud1(void)
Definition: mg_tetra.cpp:143
MAILLEUR3D_OPTIMISATION::lst_tetra
ORDRE_TETRA lst_tetra[2]
Definition: mailleur3d_optimisation.h:69
TPL_SET
Definition: tpl_set.h:34
MAILLEUR3D_OPTIMISATION::supprimer_ordre_tetra
virtual void supprimer_ordre_tetra(M3D_TETRA *tet)
Definition: mailleur3d_optimisation.cpp:610
MG_MAILLAGE::get_premier_tetra
MG_TETRA * get_premier_tetra(LISTE_MG_TETRA::iterator &it)
Definition: mg_maillage.cpp:1374
M3D_TRIANGLE
Definition: m3d_triangle.h:31
m3d_triangle.h
COQUILLE::volume
double volume
Definition: mailleur3d_optimisation.h:97
TPL_SET::get_premier
X get_premier(ITERATEUR &it)
Definition: tpl_set.h:99
MG_ELEMENT_TOPOLOGIQUE::get_dimension
virtual int get_dimension(void)=0
MAILLEUR3D_OPTIMISATION::tab_solution
int tab_solution[7][1430][8]
Definition: mailleur3d_optimisation.h:81
MAGIC_AFFICHE::affiche
virtual void affiche(char *mess)
Definition: magic_affiche.cpp:43
MAILLEUR3D_OPTIMISATION::remaille_coquille
virtual void remaille_coquille(MG_NOEUD *noeud1, MG_NOEUD *noeud2, double &crit, class COQUILLE &coque)
Definition: mailleur3d_optimisation.cpp:408
MG_TRIANGLE
Definition: mg_triangle.h:38
MG_VOLUME
Definition: mg_volume.h:33
OT_VECTEUR_3D::get_x
virtual double get_x(void) const
Definition: ot_mathematique.cpp:417
MG_TRIANGLE::noeud3
class MG_NOEUD * noeud3
Definition: mg_triangle.h:76
MG_NOEUD::change_z
virtual void change_z(double zz)
Definition: mg_noeud.cpp:128
MG_TETRA
Definition: mg_tetra.h:37
MAILLEUR3D_OPTIMISATION::MAILLEUR3D_OPTIMISATION
MAILLEUR3D_OPTIMISATION(MG_MAILLAGE *mgmai, int niv)
Definition: mailleur3d_optimisation.cpp:36
MAILLEUR3D_OPTIMISATION::get_niveau_optimisation
virtual int get_niveau_optimisation(void)
Definition: mailleur3d_optimisation.cpp:630
MG_SEGMENT::change_dimension_topo_null
virtual void change_dimension_topo_null(int num)
Definition: mg_segment.cpp:251
MAILLEUR3D_OPTIMISATION::bouge_point
virtual int bouge_point(MG_VOLUME *mgvol, class MG_NOEUD *noeud, double &crit, double &x, double &y, double &z)
Definition: mailleur3d_optimisation.cpp:274
MAILLEUR3D_OPTIMISATION::lst_tetraid
ORDRE_TETRA_PARID lst_tetraid[2]
Definition: mailleur3d_optimisation.h:70
MG_ELEMENT_TOPOLOGIQUE::get_lien_maillage
virtual TPL_SET< MG_ELEMENT_MAILLAGE * > * get_lien_maillage(void)
Definition: mg_element_topologique.cpp:62
MG_MAILLAGE::get_suivant_tetra
MG_TETRA * get_suivant_tetra(LISTE_MG_TETRA::iterator &it)
Definition: mg_maillage.cpp:1382
MAILLEUR3D_OPTIMISATION::change_niveau_optimisation
virtual void change_niveau_optimisation(int num)
Definition: mailleur3d_optimisation.cpp:625
MG_NOEUD::change_y
virtual void change_y(double yy)
Definition: mg_noeud.cpp:123
MG_SEGMENT::get_dimension_topo_null
virtual int get_dimension_topo_null(void)
Definition: mg_segment.cpp:269
MG_NOEUD::get_type_entite
virtual int get_type_entite()
Definition: mg_noeud.cpp:72
MG_NOEUD::change_x
virtual void change_x(double xx)
Definition: mg_noeud.cpp:118
MG_MAILLAGE::supprimer_mg_tetraid
int supprimer_mg_tetraid(unsigned long num)
Definition: mg_maillage.cpp:1268
MG_MAILLAGE::ajouter_mg_triangle
MG_TRIANGLE * ajouter_mg_triangle(MG_ELEMENT_TOPOLOGIQUE *topo, class MG_NOEUD *mgnoeud1, class MG_NOEUD *mgnoeud2, class MG_NOEUD *mgnoeud3, int origine, unsigned long num=0)
Definition: mg_maillage.cpp:731
MG_SEGMENT::get_noeud1
virtual MG_NOEUD * get_noeud1(void)
Definition: mg_segment.cpp:108
OPERATEUR::egal
static int egal(double a, double b, double eps)
Definition: ot_mathematique.cpp:1629
MG_NOEUD
Definition: mg_noeud.h:41
MAILLEUR3D_OPTIMISATION::cree_triangle
virtual MG_TRIANGLE * cree_triangle(class MG_VOLUME *mgvol, MG_NOEUD *noeud1, MG_NOEUD *noeud2, MG_NOEUD *noeud3, MG_SEGMENT *segment1, MG_SEGMENT *segment2, MG_SEGMENT *segment3, int origine)
Definition: mailleur3d_optimisation.cpp:656
M3D_TETRA
Definition: m3d_tetra.h:31
MG_NOEUD::get_coord
virtual double * get_coord(void)
Definition: mg_noeud.cpp:92
MG_TRIANGLE::noeud2
class MG_NOEUD * noeud2
Definition: mg_triangle.h:75
MG_TRIANGLE::segment3
class MG_SEGMENT * segment3
Definition: mg_triangle.h:80
TPL_MAP_ENTITE::ITERATEUR
std::map< unsigned long, X, std::less< unsigned long > >::iterator ITERATEUR
Definition: tpl_map_entite.h:38
MAILLEUR3D_OPTIMISATION::~MAILLEUR3D_OPTIMISATION
virtual ~MAILLEUR3D_OPTIMISATION()
Definition: mailleur3d_optimisation.cpp:58
MG_TRIANGLE::segment1
class MG_SEGMENT * segment1
Definition: mg_triangle.h:78
TPL_LISTE_ENTITE::get_nb
virtual int get_nb(void)
Definition: tpl_liste_entite.h:67
OT_VECTEUR_3D::norme
virtual void norme(void)
Definition: ot_mathematique.cpp:494
MG_NOEUD::get_lien_tetra
TPL_LISTE_ENTITE< class MG_TETRA * > * get_lien_tetra(void)
Definition: mg_noeud.cpp:175
TPL_LISTE_ENTITE::get
virtual X get(int num)
Definition: tpl_liste_entite.h:72
ot_mathematique.h
m3d_noeud.h
OPERATEUR::qualite_tetra
static double qualite_tetra(double *noeud1, double *noeud2, double *noeud3, double *noeud4)
Definition: ot_mathematique.cpp:1673
OT_VECTEUR_3D::get_y
virtual double get_y(void) const
Definition: ot_mathematique.cpp:423
MG_NOEUD::get_x
virtual double get_x(void)
Definition: mg_noeud.cpp:77
mailleur3d_optimisation.h
MG_MAILLAGE::get_mg_segment
MG_SEGMENT * get_mg_segment(unsigned int num)
Definition: mg_maillage.cpp:619
OT_VECTEUR_3D
Definition: ot_mathematique.h:94
TPL_MAP_ENTITE::ajouter
virtual void ajouter(X x)
Definition: tpl_map_entite.h:55
m3d_tetra.h
mg_maillage.h
MG_TETRA::get_noeud4
virtual MG_NOEUD * get_noeud4(void)
Definition: mg_tetra.cpp:158
MG_MAILLAGE::get_mg_triangle
MG_TRIANGLE * get_mg_triangle(unsigned int num)
Definition: mg_maillage.cpp:784
MG_NOEUD::get_lien_petit_segment
TPL_LISTE_ENTITE< class MG_SEGMENT * > * get_lien_petit_segment(void)
Definition: mg_noeud.cpp:147
MAGIC_AFFICHE::affichageactif
int affichageactif
Definition: magic_affiche.h:42
MG_ELEMENT_MAILLAGE::get_lien_topologie
MG_ELEMENT_TOPOLOGIQUE * get_lien_topologie(void)
Definition: mg_element_maillage.cpp:51
MG_TETRA::get_noeud3
virtual MG_NOEUD * get_noeud3(void)
Definition: mg_tetra.cpp:153
MAILLEUR
Definition: mailleur.h:33
OT_VECTEUR_3D::get_z
virtual double get_z(void) const
Definition: ot_mathematique.cpp:429
MG_MAILLAGE::get_mg_tetraid
MG_TETRA * get_mg_tetraid(unsigned long num)
Definition: mg_maillage.cpp:1201
OT_VECTEUR_3D::get_longueur
virtual double get_longueur(void) const
Definition: ot_mathematique.cpp:483
MG_MAILLAGE
Definition: mg_maillage.h:62
COQUILLE::tet
MG_TETRA * tet[10]
Definition: mailleur3d_optimisation.h:95
MG_TRIANGLE::noeud1
class MG_NOEUD * noeud1
Definition: mg_triangle.h:74
MG_MAILLAGE::get_nb_mg_tetra
unsigned int get_nb_mg_tetra(void)
Definition: mg_maillage.cpp:1262
M3D_TETRA::change_qualite
virtual void change_qualite(double qu)
Definition: m3d_tetra.cpp:116
M3D_TETRA::get_qualite
virtual double get_qualite(void)
Definition: m3d_tetra.cpp:111
COQUILLE
Definition: mailleur3d_optimisation.h:88
MAILLEUR3D_OPTIMISATION::get_volume
virtual double get_volume(MG_TETRA *tet)
Definition: mailleur3d_optimisation.cpp:64
MG_TRIANGLE::segment2
class MG_SEGMENT * segment2
Definition: mg_triangle.h:79
MAILLEUR3D_OPTIMISATION::niveau_optimisation
int niveau_optimisation
Definition: mailleur3d_optimisation.h:71
MG_ELEMENT_MAILLAGE::get_origine
virtual int get_origine(void)
Definition: mg_element_maillage.cpp:91
MAILLEUR3D_OPTIMISATION::tab_face
int tab_face[7][120][3]
Definition: mailleur3d_optimisation.h:82
MAILLEUR3D_OPTIMISATION::o3d_data2
virtual void o3d_data2(void)
Definition: mailleur3d_data2.cpp:31
TPL_MAP_ENTITE::get_suivant
virtual X get_suivant(ITERATEUR &it)
Definition: tpl_map_entite.h:120
MAGIC::MAILLEURFRONTALETAT::INACTIF
@ INACTIF
Definition: mg_definition.h:109
MAILLEUR3D_OPTIMISATION::o3d_data
virtual void o3d_data(void)
Definition: mailleur3d_data.cpp:30
MAGIC::ORIGINE::MAILLEUR_AUTO
@ MAILLEUR_AUTO
Definition: mg_definition.h:79
COQUILLE::new_tetra
MG_NOEUD * new_tetra[64]
Definition: mailleur3d_optimisation.h:96
MAILLEUR3D_OPTIMISATION::optimise
virtual void optimise(MG_VOLUME *mgvol)
Definition: mailleur3d_optimisation.cpp:88
MAGIC::TYPE_ENTITE::IDM3D_NOEUD
@ IDM3D_NOEUD
Definition: mg_definition.h:69
TPL_SET::get_suivant
X get_suivant(ITERATEUR &it)
Definition: tpl_set.h:107
MG_NOEUD::get_y
virtual double get_y(void)
Definition: mg_noeud.cpp:82