KratosMultiphysics
KRATOS Multiphysics (Kratos) is a framework for building parallel, multi-disciplinary simulation software, aiming at modularity, extensibility, and high performance. Kratos is written in C++, and counts with an extensive Python interface.
trilinos_elimination_builder_and_solver.h
Go to the documentation of this file.
1 // KRATOS _____ _ _ _
2 // |_ _| __(_) (_)_ __ ___ ___
3 // | || '__| | | | '_ \ / _ \/ __|
4 // | || | | | | | | | | (_) \__
5 // |_||_| |_|_|_|_| |_|\___/|___/ APPLICATION
6 //
7 // License: BSD License
8 // Kratos default license: kratos/license.txt
9 //
10 // Main authors: Riccardo Rossi
11 //
12 
13 
14 #if !defined(KRATOS_TRILINOS_RESIDUAL_BASED_ELIMINATION_BUILDER_AND_SOLVER )
15 #define KRATOS_TRILINOS_RESIDUAL_BASED_ELIMINATION_BUILDER_AND_SOLVER
16 
17 
18 /* System includes */
19 #include <set>
20 
21 /* External includes */
22 //Trilinos includes
23 #include "Epetra_Map.h"
24 #include "Epetra_Vector.h"
25 #include "Epetra_FECrsGraph.h"
26 #include "Epetra_FECrsMatrix.h"
27 #include "Epetra_IntSerialDenseVector.h"
28 #include "Epetra_SerialDenseMatrix.h"
29 #include "Epetra_SerialDenseVector.h"
30 #include "Epetra_MpiComm.h"
31 
32 /* Project includes */
33 #include "includes/define.h"
34 #include "utilities/timer.h"
36 
37 #if !defined(START_TIMER)
38 #define START_TIMER(label, rank) \
39  if (mrComm.MyPID() == rank) \
40  Timer::Start(label);
41 #endif
42 #if !defined(STOP_TIMER)
43 #define STOP_TIMER(label, rank) \
44  if (mrComm.MyPID() == rank) \
45  Timer::Stop(label);
46 #endif
47 
48 namespace Kratos
49 {
50 
111 template<class TSparseSpace,
112  class TDenseSpace,
113  class TLinearSolver //= LinearSolver<TSparseSpace,TDenseSpace>
114  >
116  : public BuilderAndSolver< TSparseSpace,TDenseSpace, TLinearSolver >
117 {
118 public:
122 
123 
125 
126  typedef TSparseSpace SparseSpaceType;
127 
129 
130  typedef typename BaseType::TDataType TDataType;
131 
133 
135 
137 
139 
143 
147 
149 
158  Epetra_MpiComm& Comm,
159  int guess_row_size,
160  typename TLinearSolver::Pointer pNewLinearSystemSolver)
161  : BuilderAndSolver< TSparseSpace,TDenseSpace,TLinearSolver >(pNewLinearSystemSolver)
162  , mrComm(Comm),mguess_row_size(guess_row_size)
163  {
164 
165 
166  /* std::cout << "using the standard builder and solver " << std::endl; */
167 
168  }
169 // TrilinosResidualBasedEliminationBuilderAndSolver(
170 // )
171 // : BaseType(typename LinearSolver<TSparseSpace,TDenseSpace>::Pointer(new LinearSolver<TSparseSpace,TDenseSpace>))
172 // {
173 //
174 // /* std::cout << "using the standard builder and solver " << std::endl; */
175 //
176 // }
177 
178 
182 
183 
189  //**************************************************************************
190  //**************************************************************************
191  void Build(
192  typename TSchemeType::Pointer pScheme,
193  ModelPart& r_model_part,
195  TSystemVectorType& b) override
196  {
197  KRATOS_TRY
198  if (!pScheme)
199  KRATOS_THROW_ERROR(std::runtime_error, "No scheme provided!", "");
200 
201  //getting the elements from the model
202  ElementsArrayType& pElements = r_model_part.Elements();
203 
204  //getting the array of the conditions
205  ConditionsArrayType& ConditionsArray = r_model_part.Conditions();
206 
207  //resetting to zero the vector of reactions
208  TSparseSpace::SetToZero(*BaseType::mpReactionsVector);
209 
210  //contributions to the system
211  LocalSystemMatrixType LHS_Contribution = LocalSystemMatrixType(0,0);
212  LocalSystemVectorType RHS_Contribution = LocalSystemVectorType(0);
213 
214  //vector containing the localization in the system of the different
215  //terms
217 
218  // int rank = A.Comm().MyPID(); //getting the processor Id
219 
220  const ProcessInfo& CurrentProcessInfo = r_model_part.GetProcessInfo();
221  // assemble all elements
222  for (typename ElementsArrayType::ptr_iterator it=pElements.ptr_begin(); it!=pElements.ptr_end(); ++it)
223  {
224  //calculate elemental contribution
225  pScheme->CalculateSystemContributions(**it,LHS_Contribution,RHS_Contribution,EquationId,CurrentProcessInfo);
226  /*KRATOS_WATCH((*it)->Id());
227  for(unsigned int i = 0; i<EquationId.size(); i++)
228  std::cout << EquationId[i] << " ";
229 
230  std::cout << std::endl;
231  KRATOS_WATCH(RHS_Contribution);*/
232  //assemble the elemental contribution
233  TSparseSpace::AssembleLHS(A,LHS_Contribution,EquationId);
234  TSparseSpace::AssembleRHS(b,RHS_Contribution,EquationId);
235  }
236 
237  LHS_Contribution.resize(0,0,false);
238  RHS_Contribution.resize(0,false);
239 
240  // assemble all conditions
241  for (typename ConditionsArrayType::ptr_iterator it=ConditionsArray.ptr_begin(); it!=ConditionsArray.ptr_end(); ++it)
242  {
243  //calculate elemental contribution
244  pScheme->CalculateSystemContributions(**it,LHS_Contribution,RHS_Contribution,EquationId,CurrentProcessInfo);
245 
246  //assemble the elemental contribution
247  TSparseSpace::AssembleLHS(A,LHS_Contribution,EquationId);
248  TSparseSpace::AssembleRHS(b,RHS_Contribution,EquationId);
249  }
250 
251  //finalizing the assembly
252  A.GlobalAssemble();
253  b.GlobalAssemble();
254 
255 
256 // std::cout << A.Comm().MyPID() << " first id " << mFirstMyId << " last id " << mLastMyId << std::endl;
257 
258  /*ModelPart::NodesContainerType::iterator node_it = r_model_part.Nodes().find(2756);
259  std::cout << A.Comm().MyPID() << " node 2756 " << node_it->FastGetSolutionStepValue(PARTITION_INDEX) << " disp_x id " << node_it->pGetDof(DISPLACEMENT_X)->EquationId() << std::endl;*/
260  KRATOS_CATCH("")
261 
262  }
263 
264  //**************************************************************************
265  //**************************************************************************
266  void BuildLHS(
267  typename TSchemeType::Pointer pScheme,
268  ModelPart& r_model_part,
269  TSystemMatrixType& A) override
270  {
271  KRATOS_TRY
272 
273  //getting the elements from the model
274  ElementsArrayType& pElements = r_model_part.Elements();
275 
276  //getting the array of the conditions
277  ConditionsArrayType& ConditionsArray = r_model_part.Conditions();
278 
279  //resetting to zero the vector of reactions
280 // TSparseSpace::SetToZero(BaseType::mReactionsVector);
281 
282  //contributions to the system
283  LocalSystemMatrixType LHS_Contribution = LocalSystemMatrixType(0,0);
284 
285  //vector containing the localization in the system of the different
286  //terms
288 
289  const ProcessInfo& CurrentProcessInfo = r_model_part.GetProcessInfo();
290 
291  // assemble all elements
292  for (typename ElementsArrayType::ptr_iterator it=pElements.ptr_begin(); it!=pElements.ptr_end(); ++it)
293  {
294  //calculate elemental contribution
295  pScheme->CalculateLHSContribution(**it,LHS_Contribution,EquationId,CurrentProcessInfo);
296 
297  //assemble the elemental contribution
298  TSparseSpace::AssembleLHS(A,LHS_Contribution,EquationId);
299  }
300 
301  LHS_Contribution.resize(0,0,false);
302 
303  // assemble all conditions
304  for (typename ConditionsArrayType::ptr_iterator it=ConditionsArray.ptr_begin(); it!=ConditionsArray.ptr_end(); ++it)
305  {
306  //calculate elemental contribution
307  pScheme->CalculateLHSContribution(**it,LHS_Contribution,EquationId,CurrentProcessInfo);
308 
309  //assemble the elemental contribution
310  TSparseSpace::AssembleLHS(A,LHS_Contribution,EquationId);
311  }
312 
313  //finalizing the assembly
314  A.GlobalAssemble();
315  KRATOS_CATCH("")
316 
317  }
318 
319 
320 
321  //**************************************************************************
322  //**************************************************************************
325  TSystemVectorType& Dx,
327  ModelPart& rModelPart
328  )
329  {
330  KRATOS_TRY
331 
332 
333  double norm_b;
334  if (TSparseSpace::Size(b) != 0)
335  norm_b = TSparseSpace::TwoNorm(b);
336  else
337  norm_b = 0.00;
338 
339  if (norm_b != 0.00)
340  {
341  if (this->GetEchoLevel()>1)
342  if (mrComm.MyPID() == 0) KRATOS_WATCH("entering in the solver");
343 
344  if(BaseType::mpLinearSystemSolver->AdditionalPhysicalDataIsNeeded() )
345  BaseType::mpLinearSystemSolver->ProvideAdditionalData(A, Dx, b, BaseType::mDofSet, rModelPart);
346 
347  this->mpLinearSystemSolver->Solve(A,Dx,b);
348 
349  }
350  else
351  {
352  TSparseSpace::SetToZero(Dx);
353  }
354 
355  //prints informations about the current time
356  if (this->GetEchoLevel()>1)
357  {
358  std::cout << *(BaseType::mpLinearSystemSolver) << std::endl;
359  }
360 
361  KRATOS_CATCH("")
362 
363  }
364 
365  //**************************************************************************
366  //**************************************************************************
368  typename TSchemeType::Pointer pScheme,
369  ModelPart& rModelPart,
370  TSystemMatrixType& rA,
371  TSystemVectorType& rDx,
372  TSystemVectorType& rb) override
373  {
374  KRATOS_TRY
375 
376  if (BaseType::GetEchoLevel() > 0)
377  START_TIMER("Build", 0)
378 
379  Build(pScheme,rModelPart,rA,rb);
380 
381  if (BaseType::GetEchoLevel() > 0)
382  STOP_TIMER("Build", 0)
383 
384  //does nothing...dirichlet conditions are naturally dealt with in defining the residual
385  ApplyDirichletConditions(pScheme,rModelPart,rA,rDx,rb);
386 
387  KRATOS_INFO_IF("TrilinosResidualBasedEliminationBuilderAndSolver", BaseType::GetEchoLevel() == 3)
388  << "\nBefore the solution of the system"
389  << "\nSystem Matrix = " << rA << "\nunknowns vector = " << rDx
390  << "\nRHS vector = " << rb << std::endl;
391 
392  if (BaseType::GetEchoLevel() > 0)
393  START_TIMER("System solve time ", 0)
394 
395  SystemSolveWithPhysics(rA,rDx,rb, rModelPart);
396 
397  if (BaseType::GetEchoLevel() > 0)
398  STOP_TIMER("System solve time ", 0)
399 
400  KRATOS_INFO_IF("TrilinosResidualBasedEliminationBuilderAndSolver", BaseType::GetEchoLevel() == 3)
401  << "\nAfter the solution of the system"
402  << "\nSystem Matrix = " << rA << "\nUnknowns vector = " << rDx
403  << "\nRHS vector = " << rb << std::endl;
404 
405  KRATOS_CATCH("")
406  }
407 
408  //**************************************************************************
409  //**************************************************************************
411  typename TSchemeType::Pointer pScheme,
412  ModelPart& r_model_part,
414  TSystemVectorType& Dx,
415  TSystemVectorType& b) override
416  {
417  KRATOS_TRY
418 
419  BuildRHS(pScheme,r_model_part,b);
420  SystemSolveWithPhysics(A,Dx,b, r_model_part);
421 
422  KRATOS_CATCH("")
423  }
424 
425  //**************************************************************************
426  //**************************************************************************
427  void BuildRHS(
428  typename TSchemeType::Pointer pScheme,
429  ModelPart& r_model_part,
430  TSystemVectorType& b) override
431  {
432  KRATOS_TRY
433 
434  //Getting the Elements
435  ElementsArrayType& pElements = r_model_part.Elements();
436 
437  //getting the array of the conditions
438  ConditionsArrayType& ConditionsArray = r_model_part.Conditions();
439 
440  const ProcessInfo& CurrentProcessInfo = r_model_part.GetProcessInfo();
441 
442  //resetting to zero the vector of reactions
443  // TSparseSpace::SetToZero(BaseType::mReactionsVector);
444 
445  //contributions to the system
446  LocalSystemVectorType RHS_Contribution = LocalSystemVectorType(0);
447 
448  //vector containing the localization in the system of the different
449  //terms
451 
452  // assemble all elements
453  for (typename ElementsArrayType::ptr_iterator it=pElements.ptr_begin(); it!=pElements.ptr_end(); ++it)
454  {
455  //calculate elemental Right Hand Side Contribution
456  pScheme->CalculateRHSContribution(**it,RHS_Contribution,EquationId,CurrentProcessInfo);
457 
458  //assemble the elemental contribution
459  TSparseSpace::AssembleRHS(b,RHS_Contribution,EquationId);
460  }
461 
462  RHS_Contribution.resize(0,false);
463 
464  // assemble all conditions
465  for (typename ConditionsArrayType::ptr_iterator it=ConditionsArray.ptr_begin(); it!=ConditionsArray.ptr_end(); ++it)
466  {
467  //calculate elemental contribution
468  pScheme->CalculateRHSContribution(**it,RHS_Contribution,EquationId,CurrentProcessInfo);
469 
470  //assemble the elemental contribution
471  TSparseSpace::AssembleRHS(b,RHS_Contribution,EquationId);
472  }
473 
474  //finalizing the assembly
475  b.GlobalAssemble();
476 
477  KRATOS_CATCH("")
478 
479  }
480  //**************************************************************************
481  //**************************************************************************
483  typename TSchemeType::Pointer pScheme,
484  ModelPart& r_model_part
485  ) override
486  {
487  KRATOS_TRY
488 
489  //Gets the array of elements from the modeler
490  ElementsArrayType& pElements = r_model_part.GetCommunicator().LocalMesh().Elements();
491  /* ElementsArrayType& pElements = r_model_part.Elements(ModelPart::Kratos_Local); */
492 
493  Element::DofsVectorType ElementalDofList;
494 
495  const ProcessInfo& CurrentProcessInfo = r_model_part.GetProcessInfo();
496 
497  DofsArrayType Doftemp;
499 
500  int rank;
501  MPI_Comm_rank(MPI_COMM_WORLD,&rank);
502 
503  for (typename ElementsArrayType::ptr_iterator it=pElements.ptr_begin(); it!=pElements.ptr_end(); ++it)
504  {
505  // gets list of Dof involved on every element
506  pScheme->GetDofList(**it,ElementalDofList,CurrentProcessInfo);
507 
508  for (typename Element::DofsVectorType::iterator i = ElementalDofList.begin() ; i != ElementalDofList.end() ; ++i)
509  {
510  Doftemp.push_back( *i );
511  }
512  }
513 
514  //taking in account conditions
515  ConditionsArrayType& pConditions = r_model_part.Conditions();
516  for (typename ConditionsArrayType::ptr_iterator it=pConditions.ptr_begin(); it!=pConditions.ptr_end(); ++it)
517  {
518  // gets list of Dof involved on every element
519  pScheme->GetDofList(**it,ElementalDofList,CurrentProcessInfo);
520 
521  for (typename Element::DofsVectorType::iterator i = ElementalDofList.begin() ; i != ElementalDofList.end() ; ++i)
522  {
523  //mDofSet.push_back(*i);
524  Doftemp.push_back( *i );
525  }
526  }
527 
528 
529  Doftemp.Unique();
530 
531 
532 
533  //arrays for communication
534  int nprocessors;
535  MPI_Comm_size(MPI_COMM_WORLD, &nprocessors);
536 
537 
538  std::vector< std::vector<unsigned int> > local_gids(nprocessors);
539  std::vector< std::vector<unsigned int> > local_ndofs(nprocessors);
540  std::vector< std::vector<unsigned int> > local_keys(nprocessors);
541  std::vector< std::vector<unsigned int> > remote_gids(nprocessors);
542  std::vector< std::vector<unsigned int> > remote_ndofs(nprocessors);
543  std::vector< std::vector<unsigned int> > remote_keys(nprocessors);
544  std::vector< int > aux_index(nprocessors,-1);
545 
546  //here we prepare to send the dofs as we computed them (for the nodes that we DO NOT OWN)
547  //the idea is to gather the correct list of dofs on the processor that owns the corresponding nodes
548  int previous_node_id = -1; //impossible id
549  int i=-1;
550  for (typename DofsArrayType::iterator dof_iterator = Doftemp.begin(); dof_iterator != Doftemp.end(); ++dof_iterator)
551  {
552  int partition_index = dof_iterator->GetSolutionStepValue(PARTITION_INDEX);
553  if(partition_index != rank)
554  {
555  if (previous_node_id != static_cast<int>(dof_iterator->Id()) || previous_node_id != static_cast<int>(dof_iterator->Id()))
556  {
557 
558  previous_node_id = dof_iterator->Id();
559  local_gids[partition_index].push_back(previous_node_id);
560  local_ndofs[partition_index].push_back(1);
561  local_keys[partition_index].push_back(dof_iterator->GetVariable().Key());
562  aux_index[partition_index]+=1;
563  }
564  else
565  {
566  local_ndofs[partition_index][aux_index[partition_index]] += 1;
567  local_keys[partition_index].push_back(dof_iterator->GetVariable().Key());
568  }
569  }
570  }
571 
572  //now send our local ndofs to the other processors using coloring
573  for (unsigned int i_color = 0; i_color < r_model_part.GetCommunicator().NeighbourIndices().size(); i_color++)
574  {
575  int destination = r_model_part.GetCommunicator().NeighbourIndices()[i_color];
576  if (destination >= 0)
577  {
578  MPI_Status status;
579  int send_tag = i_color;
580  int receive_tag = i_color;
581  //first of all obtain the number of nodes we will need to get remotely
582  int remote_gids_size;
583  int local_gids_size = local_gids[destination].size();
584  MPI_Sendrecv(&local_gids_size, 1, MPI_INT, destination, send_tag, &remote_gids_size, 1, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
585  remote_gids[destination].resize(remote_gids_size);
586  remote_ndofs[destination].resize(remote_gids_size);
587 
588  //receive the remote GiDs
589  MPI_Sendrecv(local_gids[destination].data(), local_gids[destination].size(), MPI_INT, destination, send_tag, remote_gids[destination].data(), remote_gids_size, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
590 
591  //receive the remote ndofs (same size as the gids)
592  MPI_Sendrecv(local_ndofs[destination].data(), local_ndofs[destination].size(), MPI_INT, destination, send_tag, remote_ndofs[destination].data(), remote_gids_size, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
593 
594  //find the number of non local dofs to receive
595  int remote_keys_size;
596  int local_keys_size = local_keys[destination].size();
597  MPI_Sendrecv(&local_keys_size, 1, MPI_INT, destination, send_tag, &remote_keys_size, 1, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
598  remote_keys[destination].resize(remote_keys_size);
599 
600  //receive the keys
601  MPI_Sendrecv(local_keys[destination].data(), local_keys[destination].size(), MPI_INT, destination, send_tag, remote_keys[destination].data(), remote_keys_size, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
602  }
603  }
604  //add the remote dofs to the current dof list and do an unique, so that the non-local dofs are added
605  for (int i_color=0; i_color<nprocessors; i_color++)
606  {
607  for (unsigned int i=0; i<remote_gids[i_color].size(); i++)
608  {
609  int counter = 0;
610  ModelPart::NodesContainerType::iterator it = r_model_part.Nodes().find(remote_gids[i_color][i]);
611  if(it == r_model_part.NodesEnd())
612  {
613  std::cout << "rank = "<< rank << " while communicating with " << i_color << std::endl;
614  KRATOS_THROW_ERROR(std::logic_error,"attempting to find an inexisting node with id",remote_gids[i_color][i] )
615  }
616  for (unsigned int idof=0; idof<remote_ndofs[i_color][i]; idof++) //loop over the dofs we received for node i
617  {
618  unsigned int key = remote_keys[i_color][counter++];
619 
620  Node::DofsContainerType::iterator i_dof;
621  for (i_dof = it->GetDofs().begin() ; i_dof != it->GetDofs().end() ; i_dof++)
622  if ((*i_dof)->GetVariable().Key() == key)
623  break;
624  if(i_dof == it->GetDofs().end())
625  KRATOS_THROW_ERROR(std::logic_error,"dof not found",**i_dof);
626 
627  Doftemp.push_back( i_dof.base()->get() );
628 
629  }
630  }
631  }
632  Doftemp.Unique();
633 
634  for (int i_color = 0; i_color < nprocessors; i_color++)
635  {
636  local_gids[i_color].resize(0);
637  local_gids[i_color].clear();
638  local_ndofs[i_color].resize(0);
639  local_ndofs[i_color].clear();
640  local_keys[i_color].resize(0);
641  local_keys[i_color].clear();
642  }
643 
644  //now we are sure that for the nodes we own the dofs are ok, so we repeat the operation (but this time just with the nodes we own)
645  //here we prepare to scatter the dofs which belong to the nodes we own to all of the subdomains.
646  //This is slightly involved since we only know which nodes have to be sent color b colort
647  for (unsigned int i_color = 0; i_color < r_model_part.GetCommunicator().NeighbourIndices().size(); i_color++)
648  {
649  int destination = r_model_part.GetCommunicator().NeighbourIndices()[i_color];
650  if (destination >= 0)
651  {
652  previous_node_id = -1; //impossible id
653  i=-1;
654 
655  ModelPart::NodesContainerType rLocalInterfaceNodes = r_model_part.GetCommunicator().LocalMesh(i_color).Nodes();
656 
657  for (typename DofsArrayType::iterator dof_iterator = Doftemp.begin(); dof_iterator != Doftemp.end(); ++dof_iterator)
658  {
659  if (previous_node_id != static_cast<int>(dof_iterator->Id()) )
660  {
661  if(rLocalInterfaceNodes.find(dof_iterator->Id()) != rLocalInterfaceNodes.end() )
662  {
663  previous_node_id = dof_iterator->Id();
664  local_gids[destination].push_back(previous_node_id);
665  local_ndofs[destination].push_back(1);
666  local_keys[destination].push_back(dof_iterator->GetVariable().Key());
667  i = i+1;
668  }
669  }
670  else
671  {
672  local_ndofs[destination][i] += 1;
673  local_keys[destination].push_back(dof_iterator->GetVariable().Key());
674  }
675  }
676 
677  }
678  }
679  //now send our local ndofs to the other processors using coloring
680  for (unsigned int i_color = 0; i_color < r_model_part.GetCommunicator().NeighbourIndices().size(); i_color++)
681  {
682  int destination = r_model_part.GetCommunicator().NeighbourIndices()[i_color];
683  if (destination >= 0)
684  {
685  MPI_Status status;
686  int send_tag = i_color;
687  int receive_tag = i_color;
688  //first of all obtain the number of nodes we will need to get remotely
689  int remote_gids_size;
690  int local_gids_size = local_gids[destination].size();
691  MPI_Sendrecv(&local_gids_size, 1, MPI_INT, destination, send_tag, &remote_gids_size, 1, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
692  remote_gids[destination].resize(remote_gids_size);
693  remote_ndofs[destination].resize(remote_gids_size);
694 
695  //receive the remote GiDs
696  MPI_Sendrecv(local_gids[destination].data(), local_gids[destination].size(), MPI_INT, destination, send_tag, remote_gids[destination].data(), remote_gids_size, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
697 
698  //receive the remote ndofs (same size as the gids)
699  MPI_Sendrecv(local_ndofs[destination].data(), local_ndofs[destination].size(), MPI_INT, destination, send_tag, remote_ndofs[destination].data(), remote_gids_size, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
700 
701  //find the number of non local dofs to receive
702  int remote_keys_size;
703  int local_keys_size = local_keys[destination].size();
704  MPI_Sendrecv(&local_keys_size, 1, MPI_INT, destination, send_tag, &remote_keys_size, 1, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
705  remote_keys[destination].resize(remote_keys_size);
706 
707  //receive the keys
708 
709  MPI_Sendrecv(local_keys[destination].data(), local_keys[destination].size(), MPI_INT, destination, send_tag, remote_keys[destination].data(), remote_keys_size, MPI_INT, destination, receive_tag,MPI_COMM_WORLD, &status);
710  }
711  }
712 
713  //add the remote dofs to the current dof list and do an unique, so that the local nodes are added
714 
715  for (int i_color=0; i_color<nprocessors; i_color++)
716  {
717  for (unsigned int i=0; i<remote_gids[i_color].size(); i++)
718  {
719  int counter = 0;
720  ModelPart::NodesContainerType::iterator it = r_model_part.Nodes().find(remote_gids[i_color][i]);
721  if(it == r_model_part.NodesEnd())
722  {
723  std::cout << "rank = "<< rank << " while communicating with " << i_color << std::endl;
724  KRATOS_THROW_ERROR(std::logic_error,"attempting to find an inexisting node with id",remote_gids[i_color][i] )
725  }
726  for (unsigned int idof=0; idof<remote_ndofs[i_color][i]; idof++)
727  {
728  unsigned int key = remote_keys[i_color][counter++];
729 
730  Node::DofsContainerType::iterator i_dof;
731  for (i_dof = it->GetDofs().begin() ; i_dof != it->GetDofs().end() ; i_dof++)
732  if ((*i_dof)->GetVariable().Key() == key)
733  break;
734 
735  Doftemp.push_back( i_dof.base()->get() );
736 
737  }
738  }
739  }
740 
741  //add the remote dofs to the dof list and do a final "unique"
742  Doftemp.Unique();
743 
744  BaseType::mDofSet = Doftemp;
745 
746  //throws an execption if there are no Degrees of freedom involved in the analysis
747  if (BaseType::mDofSet.size()==0)
748  KRATOS_THROW_ERROR(std::logic_error, "No degrees of freedom!", "");
749 
750  // Fixing the ghost degrees of freedom
751 // NodesArrayType& rNodes = r_model_part.Nodes(ModelPart::Kratos_Ghost);
752 // for(typename NodesArrayType::iterator i_node = rNodes.ptr_begin(); i_node != rNodes.end(); ++i_node)
753 // for(ModelPart::NodeType::DofsContainerType::iterator i_dof = i_node->GetDofs().begin() ; i_dof != i_node->GetDofs().end() ; i_dof++)
754 // i_dof->FixDof();
755 
756  // If reactions are to be calculated, we check if all the dofs have reactions defined
757  // This is tobe done only in debug mode
758 
759  #ifdef KRATOS_DEBUG
760 
762  {
763  for(auto dof_iterator = BaseType::mDofSet.begin(); dof_iterator != BaseType::mDofSet.end(); ++dof_iterator)
764  {
765  KRATOS_ERROR_IF_NOT(dof_iterator->HasReaction()) << "Reaction variable not set for the following : " <<std::endl
766  << "Node : "<<dof_iterator->Id()<< std::endl
767  << "Dof : "<<(*dof_iterator)<<std::endl<<"Not possible to calculate reactions."<<std::endl;
768  }
769  }
770  #endif
771 
772 
774 
775  KRATOS_CATCH("")
776  }
777 
778  //**************************************************************************
779  //**************************************************************************
781  ModelPart& r_model_part
782  ) override
783  {
784 
785  // Set equation id for degrees of freedom
786  // the free degrees of freedom are positioned at the beginning of the system,
787  // while the fixed one are at the end (in opposite order).
788  //
789  // that means that if the EquationId is greater than "mEquationSystemSize"
790  // the pointed degree of freedom is restrained
791  //
792  int free_size = 0;
793  int fixed_size = 0;
794 
795  int rank;
796  MPI_Comm_rank(MPI_COMM_WORLD,&rank);
797 
798  // Calculating number of fixed and free dofs
799  for (typename DofsArrayType::iterator dof_iterator = BaseType::mDofSet.begin(); dof_iterator != BaseType::mDofSet.end(); ++dof_iterator)
800  if (dof_iterator->GetSolutionStepValue(PARTITION_INDEX) == rank)
801  {
802  if (dof_iterator->IsFixed())
803  fixed_size++;
804  else
805  free_size++;
806  }
807 
808  // Calculating the total size and required offset
809  int free_offset;
810  int fixed_offset;
811  int global_size;
812 
813  // The correspounding offset by the sum of the sizes in thread with inferior rank
814  MPI_Scan(&free_size, &free_offset, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD);
815 
816  // The total size by the sum of all size in all threads
817  MPI_Allreduce(&free_size, &global_size, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD);
818 
819  // The correspounding fixed offset by the sum of the fixed sizes in thread with inferior rank
820  MPI_Scan(&fixed_size, &fixed_offset, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD);
821 
822  // finding the offset for the begining of the partition
823  free_offset -= free_size;
824 
825  fixed_offset += global_size - fixed_size;
826 
827  if (BaseType::GetEchoLevel()>1)
828  {
829  if (rank == 0)
830  {
831  std::cout << rank << " : local size = " << BaseType::mDofSet.size() << std::endl;
832  std::cout << rank << " : free_id = " << free_size << std::endl;
833  std::cout << rank << " : fixed_size = " << fixed_size << std::endl;
834  std::cout << rank << " : free_offset = " << free_offset << std::endl;
835  std::cout << rank << " : fixed offset = " << fixed_offset << std::endl;
836  }
837  }
838 
839  // Now setting the equation id with .
840  for (typename DofsArrayType::iterator dof_iterator = BaseType::mDofSet.begin(); dof_iterator != BaseType::mDofSet.end(); ++dof_iterator)
841  if (dof_iterator->GetSolutionStepValue(PARTITION_INDEX) == rank)
842  {
843  if (dof_iterator->IsFixed())
844  dof_iterator->SetEquationId(fixed_offset++);
845  else
846  dof_iterator->SetEquationId(free_offset++);
847 // std::cout << rank << " : set eq. id for dof " << dof_iterator->Id() << " to " << dof_iterator->EquationId() << std::endl;
848  }
849 
850 
851  BaseType::mEquationSystemSize = global_size;
852  mLocalSystemSize = free_size;
853 
854  if (BaseType::GetEchoLevel()>1)
855  {
856  if (rank == 0)
857  {
858  std::cout << rank << " : BaseType::mEquationSystemSize = " << BaseType::mEquationSystemSize << std::endl;
859  std::cout << rank << " : mLocalSystemSize = " << mLocalSystemSize << std::endl;
860  std::cout << rank << " : free_offset = " << free_offset << std::endl;
861  std::cout << rank << " : fixed_offset = " << fixed_offset << std::endl;
862  }
863  }
864 
865  //by Riccardo ... it may be wrong!
866  mFirstMyId = free_offset-mLocalSystemSize;
867  mLastMyId = mFirstMyId+mLocalSystemSize;
868 
869 
870 // for(ModelPart::NodesContainerType::iterator it = r_model_part.NodesBegin(); it != r_model_part.NodesEnd(); it++)
871 // {
872 // it->FastGetSolutionStepValue(REACTION_X) = it->pGetDof(DISPLACEMENT_X)->EquationId();
873 // it->FastGetSolutionStepValue(REACTION_Y) = it->pGetDof(DISPLACEMENT_Y)->EquationId();
874 // it->FastGetSolutionStepValue(REACTION_Z) = it->pGetDof(DISPLACEMENT_Z)->EquationId();
875 // }
876 
877 // for (typename DofsArrayType::iterator dof_iterator = BaseType::mDofSet.begin(); dof_iterator != BaseType::mDofSet.end(); ++dof_iterator)
878 // {
879 // if(( dof_iterator->Id() == 347) || (dof_iterator->EquationId() == 687))
880 // std::cout << rank << " : mDofSet : " << dof_iterator->Id() << " with equation id : " <<dof_iterator->EquationId() << " with partition index : " <<dof_iterator->GetSolutionStepValue(PARTITION_INDEX) << std::endl;
881 // }
882 
883 // UpdateGhostDofs(r_model_part);
884  r_model_part.GetCommunicator().SynchronizeDofs();
885 
886  /* for(ModelPart::NodesContainerType::iterator it = r_model_part.NodesBegin(); it != r_model_part.NodesEnd(); it++)
887  {
888  it->FastGetSolutionStepValue(ROTATION_X) = it->pGetDof(DISPLACEMENT_X)->EquationId();
889  it->FastGetSolutionStepValue(ROTATION_Y) = it->pGetDof(DISPLACEMENT_Y)->EquationId();
890  it->FastGetSolutionStepValue(ROTATION_Z) = it->pGetDof(DISPLACEMENT_Z)->EquationId();
891  }*/
892 
893 // std::vector<unsigned int > prova;
894 //
895 // for(ModelPart::NodesContainerType::iterator it = r_model_part.NodesBegin(); it != r_model_part.NodesEnd(); it++)
896 // {
897 // {
898 // it->FastGetSolutionStepValue(ROTATION_X) = it->pGetDof(VELOCITY_X)->EquationId();
899 // it->FastGetSolutionStepValue(ROTATION_Y) = it->pGetDof(VELOCITY_Y)->EquationId();
900 // it->FastGetSolutionStepValue(ROTATION_Z) = it->pGetDof(VELOCITY_Z)->EquationId();
901 // it->FastGetSolutionStepValue(TEMPERATURE) = it->pGetDof(PRESSURE)->EquationId();
902 // }
903 // }
904 //
905 // int prova_size = prova.size();
906 //
907 // std::cout << "number of duplicated elements = " << prova.size() - prova_size << std::endl;
908 
909  }
910 
911  void UpdateGhostDofs(ModelPart& rThisModelPart)
912  {
913  int rank;
914  MPI_Comm_rank(MPI_COMM_WORLD, &rank);
915 
916 // std::cout << rank << " : Strarting UpdateGhostDofs...." << std::endl;
917 
918  //int source=rank;
919  int destination=0;
920 
921 // vector<int>& neighbours_indices = rThisModelPart[NEIGHBOURS_INDICES];
922  vector<int>& neighbours_indices = rThisModelPart.GetCommunicator().NeighbourIndices();
923 
924 // std::cout << rank << " starting domain loop " << std::endl;
925  for (unsigned int i_domain = 0 ; i_domain < neighbours_indices.size() ; i_domain++)
926  if ((destination = neighbours_indices[i_domain]) >= 0)
927  {
928 // std::cout << rank << " domian #" << i_domain << std::endl;
929  unsigned int send_buffer_size = 0;
930  unsigned int receive_buffer_size = 0;
931 
932 // std::cout << rank;
933 // KRATOS_WATCH(destination);
934  // Calculating send and received buffer size
935  // The interface meshes are stored after all, local and ghost meshes
936  NodesArrayType& r_interface_nodes = rThisModelPart.GetCommunicator().LocalMesh(i_domain).Nodes();
937  NodesArrayType& r_ghost_nodes = rThisModelPart.GetCommunicator().GhostMesh().Nodes();
938  /* NodesArrayType& r_interface_nodes = rThisModelPart.Nodes(ModelPart::Kratos_Ownership_Size + i_domain); */
939  /* NodesArrayType& r_ghost_nodes = rThisModelPart.Nodes(ModelPart::Kratos_Ghost); */
940 
941 // std::cout << rank << " : 2...." << std::endl;
942  for (typename NodesArrayType::iterator i_node = r_interface_nodes.begin(); i_node != r_interface_nodes.end(); ++i_node)
943  send_buffer_size += i_node->GetDofs().size();
944 
945 // std::cout << rank << " : 3...." << std::endl;
946  for (typename NodesArrayType::iterator i_node = r_ghost_nodes.begin(); i_node != r_ghost_nodes.end(); ++i_node)
947  if (i_node->GetSolutionStepValue(PARTITION_INDEX) == destination)
948  {
949  receive_buffer_size += i_node->GetDofs().size();
950  /* for(ModelPart::NodeType::DofsContainerType::iterator i_dof = i_node->GetDofs().begin() ; i_dof != i_node->GetDofs().end() ; i_dof++)
951  {
952  std::cout << rank << " : receving : " << i_dof->GetVariable().Name() << " dof in node " << i_node->Id() << std::endl;
953  }*/
954  }
955  unsigned int position = 0;
956  int* send_buffer = new int[send_buffer_size];
957  int* receive_buffer = new int[receive_buffer_size];
958 
959 
960  // Filling the buffer
961  std::cout << rank << " : Filling the buffer...." << std::endl;
962  for (ModelPart::NodeIterator i_node = r_interface_nodes.begin(); i_node != r_interface_nodes.end(); ++i_node)
963  for (ModelPart::NodeType::DofsContainerType::iterator i_dof = i_node->GetDofs().begin() ; i_dof != i_node->GetDofs().end() ; i_dof++)
964  {
965  send_buffer[position++] = (*i_dof)->EquationId();
966 // std::cout << rank << " : sending equation id : " << i_dof->EquationId() << " for " << i_dof->GetVariable().Name() << " dof in node " << i_node->Id() << std::endl;
967  }
968 // {
969 // std::cout << rank << " : sending DISPLACEMENT_X eq id : " << i_node->GetDof(DISPLACEMENT_X).EquationId() << " for node " << i_node->Id() << std::endl;
970 // send_buffer[position++] = i_node->GetDof(DISPLACEMENT_X).EquationId();
971 // std::cout << rank << " : sending DISPLACEMENT_Y eq id : " << i_node->GetDof(DISPLACEMENT_Y).EquationId() << " for node " << i_node->Id() << std::endl;
972 // send_buffer[position++] = i_node->GetDof(DISPLACEMENT_Y).EquationId();
973 // std::cout << rank << " : sending DISPLACEMENT_Z eq id : " << i_node->GetDof(DISPLACEMENT_Z).EquationId() << " for node " << i_node->Id() << std::endl;
974 // send_buffer[position++] = i_node->GetDof(DISPLACEMENT_Z).EquationId();
975 // }
976 
977 
978  MPI_Status status;
979 
981  /* std::cout << rank ; */
982  /* KRATOS_WATCH(source); */
983  /* std::cout << rank ; */
984  /* KRATOS_WATCH(destination); */
985  /* int* test_send_buffer = new int[1]; */
986  /* int* test_recv_buffer = new int[1]; */
987  /* test_send_buffer[0] = rank; */
988  /* MPI_Sendrecv (test_send_buffer, 1, MPI_INT, destination, 12, test_recv_buffer, 1, MPI_INT, destination, 12, MPI_COMM_WORLD, &status); */
989  /* std::cout << rank ; */
990  /* KRATOS_WATCH(test_send_buffer[0]); */
991  /* std::cout << rank ; */
992  /* KRATOS_WATCH(test_recv_buffer[0]); */
993  /* delete [] test_send_buffer; */
994  /* delete [] test_recv_buffer; */
995 
996 
997 
998 
999 
1000 
1001 
1002 
1003 
1004 
1005 
1006  if (position > send_buffer_size)
1007  std::cout << rank << " Error in estimating send buffer size...." << std::endl;
1008 
1009 
1010  int send_tag = 1;//i_domain;
1011  int receive_tag = 1;//i_domain;
1012  // int rc;
1013 
1014 // std::cout << rank << " : Strarting Send and receive...." << std::endl;
1015 // std::cout << rank ;
1016 // KRATOS_WATCH(source);
1017 // std::cout << rank ;
1018 // KRATOS_WATCH(destination);
1019 // std::cout << rank ;
1020 // KRATOS_WATCH(send_buffer_size);
1021 // std::cout << rank ;
1022 // KRATOS_WATCH(receive_buffer_size);
1023 // std::cout << rank ;
1024 // KRATOS_WATCH(send_tag);
1025 // std::cout << rank ;
1026 // KRATOS_WATCH(receive_tag);
1027 
1028 
1029  MPI_Sendrecv (send_buffer, send_buffer_size, MPI_INT, destination, send_tag, receive_buffer, receive_buffer_size, MPI_INT, destination, receive_tag,
1030  MPI_COMM_WORLD, &status);
1031 
1032 // std::cout << rank << " : Send and receive Finished" << std::endl;
1033 
1034  // Updating nodes
1035  position = 0;
1036  for (ModelPart::NodeIterator i_node = rThisModelPart.GetCommunicator().GhostMesh().NodesBegin() ;
1037  i_node != rThisModelPart.GetCommunicator().GhostMesh().NodesEnd() ; i_node++)
1038 // for(ModelPart::NodeIterator i_node = rThisModelPart.NodesBegin(ModelPart::Kratos_Ghost) ;
1039 // i_node != rThisModelPart.NodesEnd(ModelPart::Kratos_Ghost) ; i_node++)
1040  if (i_node->GetSolutionStepValue(PARTITION_INDEX) == destination)
1041  for (ModelPart::NodeType::DofsContainerType::iterator i_dof = i_node->GetDofs().begin() ; i_dof != i_node->GetDofs().end() ; i_dof++)
1042  {
1043  (*i_dof)->SetEquationId(receive_buffer[position++]);
1044  // std::cout << rank << " : receiving equation id : " << i_dof->EquationId() << " for " << i_dof->GetVariable().Name() << " dof in node " << i_node->Id() << std::endl;
1045  }
1046  // {
1047  // i_node->GetDof(DISPLACEMENT_X).SetEquationId(receive_buffer[position++]);
1048  // i_node->GetDof(DISPLACEMENT_Y).SetEquationId(receive_buffer[position++]);
1049  // i_node->GetDof(DISPLACEMENT_Z).SetEquationId(receive_buffer[position++]);
1050  // }
1051 
1052  if (position > receive_buffer_size)
1053  std::cout << rank << " Error in estimating receive buffer size...." << std::endl;
1054 
1055  delete [] send_buffer;
1056  delete [] receive_buffer;
1057  }
1058 
1059  }
1060 
1061  //**************************************************************************
1062  //**************************************************************************
1064  typename TSchemeType::Pointer pScheme,
1068  ModelPart& rModelPart
1069  ) override
1070  {
1071  KRATOS_TRY
1072  if (this->GetEchoLevel()>1)
1073  std::cout << "entering ResizeAndInitializeVectors" << std::endl;
1074 
1075  //resizing the system vectors and matrix
1076  if ( pA == NULL || TSparseSpace::Size1(*pA) == 0 || BaseType::GetReshapeMatrixFlag() == true) //if the matrix is not initialized
1077  {
1078  //creating a work array
1079  unsigned int number_of_local_dofs = mLastMyId - mFirstMyId;
1080 
1081  int temp_size = number_of_local_dofs;
1082  if (temp_size <1000) temp_size = 1000;
1083  int* temp = new int[temp_size]; //
1084  int* assembling_temp = new int[temp_size];
1085 
1086 
1087  //generate map - use the "temp" array here
1088  for (unsigned int i=0; i!=number_of_local_dofs; i++)
1089  temp[i] = mFirstMyId+i;
1090  Epetra_Map my_map(-1, number_of_local_dofs, temp, 0, mrComm);
1091 
1092  auto& rElements = rModelPart.Elements();
1093  auto& rConditions = rModelPart.Conditions();
1094 
1095  //create and fill the graph of the matrix --> the temp array is reused here with a different meaning
1096  Epetra_FECrsGraph Agraph(Copy, my_map, mguess_row_size);
1097 
1098  Element::EquationIdVectorType EquationId;
1099  const ProcessInfo &CurrentProcessInfo = rModelPart.GetProcessInfo();
1100 
1101  // assemble all elements
1102  for (typename ElementsArrayType::ptr_iterator it=rElements.ptr_begin(); it!=rElements.ptr_end(); ++it)
1103  {
1104  pScheme->EquationId( **it, EquationId, CurrentProcessInfo );
1105 
1106  //filling the list of active global indices (non fixed)
1107  unsigned int num_active_indices = 0;
1108  for (unsigned int i=0; i<EquationId.size(); i++)
1109  {
1110  if ( EquationId[i] < BaseType::mEquationSystemSize )
1111  {
1112  assembling_temp[num_active_indices] = EquationId[i];
1113  num_active_indices += 1;
1114  }
1115  }
1116 
1117  if (num_active_indices != 0)
1118  {
1119  int ierr = Agraph.InsertGlobalIndices(num_active_indices,assembling_temp,num_active_indices, assembling_temp);
1120  KRATOS_ERROR_IF( ierr < 0 ) << "In " << __FILE__ << ":" << __LINE__ << ": Epetra failure in Graph.InsertGlobalIndices. Error code: " << ierr << std::endl;
1121  }
1122  }
1123 
1124  // assemble all conditions
1125  for (typename ConditionsArrayType::ptr_iterator it=rConditions.ptr_begin(); it!=rConditions.ptr_end(); ++it)
1126  {
1127  pScheme->EquationId( **it, EquationId, CurrentProcessInfo );
1128 
1129  //filling the list of active global indices (non fixed)
1130  unsigned int num_active_indices = 0;
1131  for (unsigned int i=0; i<EquationId.size(); i++)
1132  {
1133  if ( EquationId[i] < BaseType::mEquationSystemSize )
1134  {
1135  assembling_temp[num_active_indices] = EquationId[i];
1136  num_active_indices += 1;
1137  }
1138  }
1139 
1140  if (num_active_indices != 0)
1141  {
1142  int ierr = Agraph.InsertGlobalIndices(num_active_indices,assembling_temp,num_active_indices, assembling_temp);
1143  KRATOS_ERROR_IF( ierr < 0 ) << "In " << __FILE__ << ":" << __LINE__ << ": Epetra failure in Graph.InsertGlobalIndices. Error code: " << ierr << std::endl;
1144  }
1145  }
1146 
1147  //finalizing graph construction
1148  int ierr = Agraph.GlobalAssemble();
1149  KRATOS_ERROR_IF( ierr != 0 ) << "In " << __FILE__ << ":" << __LINE__ << ": Epetra failure in Graph.GlobalAssemble, Error code: " << ierr << std::endl;
1150 
1151  //generate a new matrix pointer according to this graph
1153  pA.swap(pNewA);
1154 
1155  //generate new vector pointers according to the given map
1156  if ( pb == NULL || TSparseSpace::Size(*pb) != BaseType::mEquationSystemSize)
1157  {
1159  pb.swap(pNewb);
1160  }
1161  if ( pDx == NULL || TSparseSpace::Size(*pDx) != BaseType::mEquationSystemSize)
1162  {
1164  pDx.swap(pNewDx);
1165  }
1166  if ( BaseType::mpReactionsVector == NULL) //if the pointer is not initialized initialize it to an empty matrix
1167  {
1168  TSystemVectorPointerType pNewReactionsVector = TSystemVectorPointerType(new TSystemVectorType(my_map) );
1169  BaseType::mpReactionsVector.swap(pNewReactionsVector);
1170  }
1171 
1172  delete [] temp;
1173  delete [] assembling_temp;
1174  }
1175  else
1176  {
1178  {
1179  KRATOS_THROW_ERROR(std::logic_error,"it should not come here resizing is not allowed this way!!!!!!!! ... ","");
1180  }
1181  }
1182 
1183  //if needed resize the vector for the calculation of reactions
1185  {
1186  KRATOS_THROW_ERROR(std::logic_error,"calculation of reactions not yet implemented with Trilinos","");
1187  }
1188 
1189  KRATOS_CATCH("")
1190  }
1191 
1192 
1193 
1194  //**************************************************************************
1195  //**************************************************************************
1197  ModelPart& r_model_part,
1199  TSystemVectorType& Dx,
1200  TSystemVectorType& b) override
1201  {
1202  KRATOS_TRY
1203  KRATOS_CATCH("")
1204  }
1205 
1206  //**************************************************************************
1207  //**************************************************************************
1209  ModelPart& r_model_part,
1211  TSystemVectorType& Dx,
1212  TSystemVectorType& b) override
1213  {
1214  }
1215 
1216 
1217  //**************************************************************************
1218  //**************************************************************************
1220  typename TSchemeType::Pointer pScheme,
1221  ModelPart& r_model_part,
1223  TSystemVectorType& Dx,
1224  TSystemVectorType& b) override
1225  {
1226 // //refresh RHS to have the correct reactions
1227 // BuildRHS(pScheme,r_model_part,b);
1228 
1229 // int i;
1230 // int systemsize = BaseType::mDofSet.size() - SparseSpaceType::Size(BaseType::mReactionsVector);
1231 
1232 // typename DofsArrayType::ptr_iterator it2;
1233 // //std::set<Dof::Pointer,ComparePDof>::iterator it2;
1234 
1235 // //updating variables
1236 // //for (it2=mDofSet.begin();it2 != mDofSet.end(); ++it2)
1237 // for (it2=BaseType::mDofSet.ptr_begin();it2 != BaseType::mDofSet.ptr_end(); ++it2)
1238 // {
1239 // if ( (*it2)->IsFixed() )
1240 // {
1241 // i=(*it2)->EquationId();
1242 // i-=systemsize;
1243 
1244 // VecGetValues(BaseType::mReactionsVector, 1, &i, &(*it2)->GetSolutionStepReactionValue());
1245 // }
1246 // }
1247  }
1248 
1250  typename TSchemeType::Pointer pScheme,
1251  ModelPart& r_model_part,
1252  TSystemMatrixType& A) override
1253  {
1254  KRATOS_THROW_ERROR(std::logic_error,"method BuildLHS_CompleteOnFreeRows not implemented in Trilinos Builder And Solver ","");
1255  }
1256 
1257  //**************************************************************************
1258  //**************************************************************************
1260  typename TSchemeType::Pointer pScheme,
1261  ModelPart& r_model_part,
1263  TSystemVectorType& Dx,
1264  TSystemVectorType& b) override
1265  {}
1266 
1289 protected:
1297  Epetra_MpiComm& mrComm;
1301 
1302 
1330 private:
1339  unsigned int mLocalSystemSize;
1340 
1351  //**************************************************************************
1352  void AssembleLHS_CompleteOnFreeRows(
1354  LocalSystemMatrixType& LHS_Contribution,
1355  Element::EquationIdVectorType& EquationId
1356  )
1357  {
1358  KRATOS_THROW_ERROR(std::logic_error, "This method is not implemented for Trilinos", "");
1359  }
1360 
1378 }; /* Class TrilinosResidualBasedEliminationBuilderAndSolver */
1379 
1388 } /* namespace Kratos.*/
1389 
1390 #endif /* KRATOS_TRILINOS_RESIDUAL_BASED_ELIMINATION_BUILDER_AND_SOLVER defined */
Current class provides an implementation for the base builder and solving operations.
Definition: builder_and_solver.h:64
bool mDofSetIsInitialized
If the matrix is reshaped each step.
Definition: builder_and_solver.h:743
TSparseSpace::VectorType TSystemVectorType
Definition of the vector size.
Definition: builder_and_solver.h:85
ModelPart::NodesContainerType NodesArrayType
The containers of the entities.
Definition: builder_and_solver.h:109
bool GetCalculateReactionsFlag() const
This method returns the flag mCalculateReactionsFlag.
Definition: builder_and_solver.h:184
TSparseSpace::MatrixType TSystemMatrixType
Definition of the sparse matrix.
Definition: builder_and_solver.h:82
ModelPart::ConditionsContainerType ConditionsArrayType
Definition: builder_and_solver.h:111
TSystemVectorPointerType mpReactionsVector
Definition: builder_and_solver.h:751
bool GetReshapeMatrixFlag() const
This method returns the flag mReshapeMatrixFlag.
Definition: builder_and_solver.h:220
TDenseSpace::MatrixType LocalSystemMatrixType
The local matrix definition.
Definition: builder_and_solver.h:94
TSparseSpace::VectorPointerType TSystemVectorPointerType
Definition of the pointer to the vector.
Definition: builder_and_solver.h:91
TSparseSpace::DataType TDataType
Definition of the data type.
Definition: builder_and_solver.h:79
TLinearSolver::Pointer mpLinearSystemSolver
Definition: builder_and_solver.h:737
DofsArrayType mDofSet
Pointer to the linear solver.
Definition: builder_and_solver.h:739
TDenseSpace::VectorType LocalSystemVectorType
The local vector definition.
Definition: builder_and_solver.h:97
TSparseSpace::MatrixPointerType TSystemMatrixPointerType
Definition of the pointer to the sparse matrix.
Definition: builder_and_solver.h:88
bool mCalculateReactionsFlag
Flag taking care if the dof set was initialized ot not.
Definition: builder_and_solver.h:745
int GetEchoLevel() const
It returns the echo level.
Definition: builder_and_solver.h:674
unsigned int mEquationSystemSize
Flag taking in account if it is needed or not to calculate the reactions.
Definition: builder_and_solver.h:747
ModelPart::ElementsContainerType ElementsArrayType
Definition: builder_and_solver.h:110
NeighbourIndicesContainerType & NeighbourIndices()
Definition: communicator.cpp:162
MeshType & GhostMesh()
Returns the reference to the mesh storing all ghost entities.
Definition: communicator.cpp:251
virtual bool SynchronizeDofs()
Definition: communicator.cpp:352
MeshType & LocalMesh()
Returns the reference to the mesh storing all local entities.
Definition: communicator.cpp:245
std::vector< DofType::Pointer > DofsVectorType
Definition: element.h:100
std::vector< std::size_t > EquationIdVectorType
Definition: element.h:98
NodesContainerType & Nodes()
Definition: mesh.h:346
NodeIterator NodesEnd()
Definition: mesh.h:336
NodeIterator NodesBegin()
Definition: mesh.h:326
ElementsContainerType & Elements()
Definition: mesh.h:568
This class aims to manage meshes for multi-physics simulations.
Definition: model_part.h:77
Communicator & GetCommunicator()
Definition: model_part.h:1821
ConditionsContainerType & Conditions(IndexType ThisIndex=0)
Definition: model_part.h:1381
ProcessInfo & GetProcessInfo()
Definition: model_part.h:1746
MeshType::NodeIterator NodeIterator
Definition: model_part.h:134
ElementsContainerType & Elements(IndexType ThisIndex=0)
Definition: model_part.h:1189
MeshType::NodesContainerType NodesContainerType
Nodes container. Which is a vector set of nodes with their Id's as key.
Definition: model_part.h:128
NodeIterator NodesEnd(IndexType ThisIndex=0)
Definition: model_part.h:497
NodesContainerType & Nodes(IndexType ThisIndex=0)
Definition: model_part.h:507
A sorted associative container similar to an STL set, but uses a vector to store pointers to its data...
Definition: pointer_vector_set.h:72
void Unique()
Remove duplicate elements from the set.
Definition: pointer_vector_set.h:764
boost::indirect_iterator< typename TContainerType::iterator > iterator
Definition: pointer_vector_set.h:95
size_type size() const
Returns the number of elements in the container.
Definition: pointer_vector_set.h:502
void push_back(TPointerType x)
Adds a pointer to the end of the set.
Definition: pointer_vector_set.h:544
iterator begin()
Returns an iterator pointing to the beginning of the container.
Definition: pointer_vector_set.h:278
iterator end()
Returns an iterator pointing to the end of the container.
Definition: pointer_vector_set.h:314
ProcessInfo holds the current value of different solution parameters.
Definition: process_info.h:59
This class provides the implementation of the basic tasks that are needed by the solution strategy.
Definition: scheme.h:56
Definition: trilinos_elimination_builder_and_solver.h:117
void ResizeAndInitializeVectors(typename TSchemeType::Pointer pScheme, TSystemMatrixPointerType &pA, TSystemVectorPointerType &pDx, TSystemVectorPointerType &pb, ModelPart &rModelPart) override
This method initializes and resizes the system of equations.
Definition: trilinos_elimination_builder_and_solver.h:1063
void BuildAndSolve(typename TSchemeType::Pointer pScheme, ModelPart &rModelPart, TSystemMatrixType &rA, TSystemVectorType &rDx, TSystemVectorType &rb) override
Function to perform the building and solving phase at the same time.
Definition: trilinos_elimination_builder_and_solver.h:367
void Build(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part, TSystemMatrixType &A, TSystemVectorType &b) override
equivalent (but generally faster) then performing BuildLHS and BuildRHS
Definition: trilinos_elimination_builder_and_solver.h:191
int mLastMyId
Definition: trilinos_elimination_builder_and_solver.h:1300
void BuildRHS(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part, TSystemVectorType &b) override
Function to perform the build of the RHS. The vector could be sized as the total number of dofs or as...
Definition: trilinos_elimination_builder_and_solver.h:427
BaseType::TSystemMatrixType TSystemMatrixType
Definition: trilinos_elimination_builder_and_solver.h:134
void SetUpDofSet(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part) override
Builds the list of the DofSets involved in the problem by "asking" to each element and condition its ...
Definition: trilinos_elimination_builder_and_solver.h:482
void UpdateGhostDofs(ModelPart &rThisModelPart)
Definition: trilinos_elimination_builder_and_solver.h:911
void SetUpSystem(ModelPart &r_model_part) override
It organises the dofset in order to speed up the building phase.
Definition: trilinos_elimination_builder_and_solver.h:780
BaseType::LocalSystemVectorType LocalSystemVectorType
Definition: trilinos_elimination_builder_and_solver.h:138
KRATOS_CLASS_POINTER_DEFINITION(TrilinosResidualBasedEliminationBuilderAndSolver)
void BuildRHSAndSolve(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part, TSystemMatrixType &A, TSystemVectorType &Dx, TSystemVectorType &b) override
Corresponds to the previews, but the System's matrix is considered already built and only the RHS is ...
Definition: trilinos_elimination_builder_and_solver.h:410
int mguess_row_size
Definition: trilinos_elimination_builder_and_solver.h:1298
BaseType::ElementsContainerType ElementsContainerType
Definition: trilinos_elimination_builder_and_solver.h:148
BaseType::TSchemeType TSchemeType
Definition: trilinos_elimination_builder_and_solver.h:128
Epetra_MpiComm & mrComm
Definition: trilinos_elimination_builder_and_solver.h:1297
BaseType::TSystemVectorPointerType TSystemVectorPointerType
Definition: trilinos_elimination_builder_and_solver.h:142
void ApplyDirichletConditions(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part, TSystemMatrixType &A, TSystemVectorType &Dx, TSystemVectorType &b) override
It applies the dirichlet conditions. This operation may be very heavy or completely unexpensive depen...
Definition: trilinos_elimination_builder_and_solver.h:1259
BaseType::NodesArrayType NodesArrayType
Definition: trilinos_elimination_builder_and_solver.h:144
virtual ~TrilinosResidualBasedEliminationBuilderAndSolver()
Definition: trilinos_elimination_builder_and_solver.h:181
BaseType::ElementsArrayType ElementsArrayType
Definition: trilinos_elimination_builder_and_solver.h:145
BaseType::TDataType TDataType
Definition: trilinos_elimination_builder_and_solver.h:130
void InitializeSolutionStep(ModelPart &r_model_part, TSystemMatrixType &A, TSystemVectorType &Dx, TSystemVectorType &b) override
It applies certain operations at the system of equations at the beginning of the solution step.
Definition: trilinos_elimination_builder_and_solver.h:1196
BaseType::TSystemVectorType TSystemVectorType
Definition: trilinos_elimination_builder_and_solver.h:136
TSparseSpace SparseSpaceType
Definition: trilinos_elimination_builder_and_solver.h:126
void SystemSolveWithPhysics(TSystemMatrixType &A, TSystemVectorType &Dx, TSystemVectorType &b, ModelPart &rModelPart)
Definition: trilinos_elimination_builder_and_solver.h:323
BaseType::TSystemMatrixPointerType TSystemMatrixPointerType
Definition: trilinos_elimination_builder_and_solver.h:141
BaseType::ConditionsArrayType ConditionsArrayType
Definition: trilinos_elimination_builder_and_solver.h:146
void BuildLHS(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part, TSystemMatrixType &A) override
Function to perform the building of the LHS, depending on the implementation chosen the size of the m...
Definition: trilinos_elimination_builder_and_solver.h:266
void CalculateReactions(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part, TSystemMatrixType &A, TSystemVectorType &Dx, TSystemVectorType &b) override
It computes the reactions of the system.
Definition: trilinos_elimination_builder_and_solver.h:1219
BuilderAndSolver< TSparseSpace, TDenseSpace, TLinearSolver > BaseType
Definition: trilinos_elimination_builder_and_solver.h:124
void BuildLHS_CompleteOnFreeRows(typename TSchemeType::Pointer pScheme, ModelPart &r_model_part, TSystemMatrixType &A) override
It builds a rectangular matrix of size n*N where "n" is the number of unrestrained degrees of freedom...
Definition: trilinos_elimination_builder_and_solver.h:1249
BaseType::LocalSystemMatrixType LocalSystemMatrixType
Definition: trilinos_elimination_builder_and_solver.h:140
BaseType::DofsArrayType DofsArrayType
Definition: trilinos_elimination_builder_and_solver.h:132
TrilinosResidualBasedEliminationBuilderAndSolver(Epetra_MpiComm &Comm, int guess_row_size, typename TLinearSolver::Pointer pNewLinearSystemSolver)
Definition: trilinos_elimination_builder_and_solver.h:157
void FinalizeSolutionStep(ModelPart &r_model_part, TSystemMatrixType &A, TSystemVectorType &Dx, TSystemVectorType &b) override
It applies certain operations at the system of equations at the end of the solution step.
Definition: trilinos_elimination_builder_and_solver.h:1208
int mFirstMyId
Definition: trilinos_elimination_builder_and_solver.h:1299
#define KRATOS_THROW_ERROR(ExceptionType, ErrorMessage, MoreInfo)
Definition: define.h:77
#define KRATOS_CATCH(MoreInfo)
Definition: define.h:110
#define KRATOS_WATCH(variable)
Definition: define.h:806
#define KRATOS_TRY
Definition: define.h:109
#define KRATOS_ERROR_IF_NOT(conditional)
Definition: exception.h:163
#define KRATOS_ERROR_IF(conditional)
Definition: exception.h:162
#define KRATOS_INFO_IF(label, conditional)
Definition: logger.h:251
TSpaceType::IndexType Size1(TSpaceType &dummy, typename TSpaceType::MatrixType const &rM)
Definition: add_strategies_to_python.cpp:117
TSpaceType::IndexType Size2(TSpaceType &dummy, typename TSpaceType::MatrixType const &rM)
Definition: add_strategies_to_python.cpp:123
double TwoNorm(SparseSpaceType &dummy, SparseSpaceType::VectorType &x)
Definition: add_strategies_to_python.cpp:164
TSpaceType::IndexType Size(TSpaceType &dummy, typename TSpaceType::VectorType const &rV)
Definition: add_strategies_to_python.cpp:111
REF: G. R. Cowper, GAUSSIAN QUADRATURE FORMULAS FOR TRIANGLES.
Definition: mesh_condition.cpp:21
b
Definition: generate_total_lagrangian_mixed_volumetric_strain_element.py:31
data
Definition: mesh_to_mdpa_converter.py:59
float temp
Definition: rotating_cone.py:85
int counter
Definition: script_THERMAL_CORRECT.py:218
A
Definition: sensitivityMatrix.py:70
integer i
Definition: TensorModule.f:17
#define STOP_TIMER(label, rank)
Definition: trilinos_elimination_builder_and_solver.h:43
#define START_TIMER(label, rank)
Definition: trilinos_elimination_builder_and_solver.h:38