Salome HOME
Get relevant changes from V7_dev branch (copyright update, adm files etc)
[tools/medcoupling.git] / src / MEDPartitioner / MEDPARTITIONER_ScotchGraph.cxx
1 // Copyright (C) 2007-2016  CEA/DEN, EDF R&D
2 //
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License, or (at your option) any later version.
7 //
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19
20 #include "MEDPARTITIONER_Graph.hxx"
21 #include "MEDPARTITIONER_ScotchGraph.hxx"
22 #include "MEDPARTITIONER_Utils.hxx"
23
24 #include "MEDCouplingSkyLineArray.hxx"
25
26 #include <cstdio>
27
28 #ifdef MED_ENABLE_SCOTCH
29 extern "C"
30 {
31 #define restrict
32 #include "scotch.h"
33 }
34 #endif
35
36 using namespace MEDPARTITIONER;
37   
38 SCOTCHGraph::SCOTCHGraph():Graph()
39 {
40 }
41
42 SCOTCHGraph::SCOTCHGraph(MEDCoupling::MEDCouplingSkyLineArray* graph, int* edgeweight):Graph(graph,edgeweight)
43 {
44 }
45
46 SCOTCHGraph::~SCOTCHGraph()
47 {
48 }
49
50 void SCOTCHGraph::partGraph(int ndomain, const std::string& options_string, ParaDomainSelector* sel)
51 {
52   if (MyGlobals::_Verbose>10)
53     std::cout << "proc " << MyGlobals::_Rank << " : SCOTCHGraph::partGraph" << std::endl;
54   
55   //number of graph vertices
56   int n = _graph->getNumberOf();
57   //graph
58   int * xadj=const_cast<int*>(_graph->getIndex());
59   int * adjncy=const_cast<int*>(_graph->getValue());
60   //ndomain
61   int nparts=ndomain;
62
63 #if !defined(MED_ENABLE_SCOTCH)
64   throw INTERP_KERNEL::Exception("SCOTCHGraph::partGraph : SCOTCH is not available. Check your products, please.");
65 #else
66   //output parameters
67   int* partition = new int[n+1];
68   
69   SCOTCH_Graph scotch_graph;
70   SCOTCH_graphInit(&scotch_graph);
71   SCOTCH_graphBuild(&scotch_graph,
72                     0, //base first indice 0
73                     n, //nb of graph nodes
74                     xadj,
75                     0,
76                     _cell_weight, //graph vertices loads
77                     0,
78                     xadj[n], //number of edges
79                     adjncy,
80                     _edge_weight);
81   SCOTCH_Strat scotch_strategy;
82   SCOTCH_stratInit(&scotch_strategy);
83   
84   //!user-defined options for the strategy
85   if (options_string!="")
86     SCOTCH_stratGraphMap(&scotch_strategy,options_string.c_str());
87
88   if (nparts>1)
89     {
90       if (MyGlobals::_Verbose>10) std::cout << "SCOTCHGraph::graphPart SCOTCH_graphPart" << std::endl;
91       SCOTCH_graphPart(&scotch_graph,nparts,&scotch_strategy,partition);
92     }
93   else  //partition for 1 subdomain
94     {
95     for (int i=0; i<n+1; i++)
96       partition[i]=0;
97     }
98   
99   SCOTCH_stratExit(&scotch_strategy);
100   SCOTCH_graphExit(&scotch_graph);
101
102   std::vector<int> index(n+1);
103   std::vector<int> value(n);
104   index[0]=0;
105   for (int i=0; i<n; i++)
106     {
107       index[i+1]=index[i]+1;
108       value[i]=partition[i];
109     }
110   delete [] partition;
111   
112   //creating a skylinearray with no copy of the index and partition array
113   //the fifth argument true specifies that only the pointers are passed 
114   //to the object
115   _partition = new MEDCoupling::MEDCouplingSkyLineArray(index,value);
116 #endif
117 }