20#pragma GCC diagnostic ignored "-Wdeprecated-copy"
21#pragma GCC diagnostic ignored "-Wint-in-bool-context"
23#include <boost/range/iterator_range.hpp>
24#include <boost/scope_exit.hpp>
26#include "arccore/alina/IO.h"
27#include "arccore/alina/Adapters.h"
28#include "arccore/alina/BuiltinBackend.h"
29#include "arccore/alina/DistributedPreconditionedSolver.h"
30#include "arccore/alina/DistributedCPRPreconditioner.h"
31#include "arccore/alina/DistributedAMG.h"
32#include "arccore/alina/DistributedCoarseningRuntime.h"
33#include "arccore/alina/DistributedRelaxationRuntime.h"
34#include "arccore/alina/DistributedSolverRuntime.h"
35#include "arccore/alina/DistributedDirectSolverRuntime.h"
36#include "arccore/alina/MatrixPartitionerRuntime.h"
37#include "arccore/alina/Profiler.h"
38#include "arccore/alina/AlinaUtils.h"
40#include "arccore/common/internal/ProgramOptions.h"
43using namespace Arcane::Alina;
45using Alina::precondition;
50 const std::string& A_file,
const std::string& rhs_file,
int block_size,
51 std::vector<ptrdiff_t>& ptr,
52 std::vector<ptrdiff_t>& col,
53 std::vector<double>& val,
54 std::vector<double>& rhs)
57 ptrdiff_t n = A_mm.rows();
59 ptrdiff_t chunk = (n + comm.size - 1) / comm.size;
60 if (chunk % block_size != 0) {
61 chunk += block_size - chunk % block_size;
64 ptrdiff_t row_beg = std::min(n, chunk * comm.rank);
65 ptrdiff_t row_end = std::min(n, row_beg + chunk);
67 chunk = row_end - row_beg;
69 A_mm(ptr, col, val, row_beg, row_end);
71 if (rhs_file.empty()) {
73 std::fill(rhs.begin(), rhs.end(), 1.0);
77 rhs_mm(rhs, row_beg, row_end);
86 const std::string& A_file,
const std::string& rhs_file,
int block_size,
87 std::vector<ptrdiff_t>& ptr,
88 std::vector<ptrdiff_t>& col,
89 std::vector<double>& val,
90 std::vector<double>& rhs)
92 ptrdiff_t n = Alina::IO::crs_size<ptrdiff_t>(A_file);
94 ptrdiff_t chunk = (n + comm.size - 1) / comm.size;
95 if (chunk % block_size != 0) {
96 chunk += block_size - chunk % block_size;
99 ptrdiff_t row_beg = std::min(n, chunk * comm.rank);
100 ptrdiff_t row_end = std::min(n, row_beg + chunk);
102 chunk = row_end - row_beg;
104 Alina::IO::read_crs(A_file, n, ptr, col, val, row_beg, row_end);
106 if (rhs_file.empty()) {
108 std::fill(rhs.begin(), rhs.end(), 1.0);
111 ptrdiff_t rows, cols;
112 Alina::IO::read_dense(rhs_file, rows, cols, rhs, row_beg, row_end);
119template <
class Backend,
class Matrix>
120std::shared_ptr<Alina::DistributedMatrix<Backend>>
123 Alina::eMatrixPartitionerType ptype,
int block_size = 1)
125 auto& prof = Alina::Profiler::globalProfiler();
128 auto A = std::make_shared<DMatrix>(comm, Astrip);
130 if (comm.size == 1 || ptype == Alina::eMatrixPartitionerType::merge)
133 prof.tic(
"partition");
135 prm.put(
"type", ptype);
138 auto I = part(*A, block_size);
139 auto J = transpose(*I);
140 A = product(*J, *product(*A, *I));
142 std::vector<double> new_rhs(J->loc_rows());
144 J->move_to_backend(bprm);
146 Alina::backend::spmv(1, *J, rhs, 0, new_rhs);
148 prof.toc(
"partition");
155int main(
int argc,
char* argv[])
157 auto& prof = Alina::Profiler::globalProfiler();
159 MPI_Init_thread(&argc, &argv, MPI_THREAD_MULTIPLE, &provided);
160 BOOST_SCOPE_EXIT(
void)
169 std::cout <<
"World size: " << comm.size << std::endl;
172 namespace po = Arcane::ProgramOptions;
175 desc.add_options()(
"help,h",
"affiche l'aide")(
"matrix,A",
176 po::value<std::string>(),
177 "Matrice du système au format MatrixMarket. "
178 "Si non spécifié, un problème de Poisson dans un cube unitaire 3D est assemblé. ")(
180 po::value<std::string>()->default_value(
""),
181 "Le vecteur du membre de droite (RHS) au format MatrixMarket. "
182 "S'il est omis, un vecteur de uns est utilisé par défaut. "
183 "Ne doit être fourni qu'avec une matrice de système. ")(
185 po::bool_switch()->default_value(
false),
186 "Si spécifié, traiter les fichiers d'entrée comme binaires au lieu de MatrixMarket. "
187 "Il est supposé que les fichiers ont été convertis au format binaire avec l'utilitaire mm2bin. ")(
189 po::value<int>()->default_value(1),
190 "La taille de bloc de la matrice de système. ")(
192 po::value<Alina::eMatrixPartitionerType>()->default_value(
193#
if defined(ARCCORE_ALINA_HAVE_PARMETIS)
194 Alina::eMatrixPartitionerType::parmetis
197 "Répartition de la matrice de système")(
"prm-file,P",
198 po::value<std::string>(),
199 "Fichier de paramètres au format json. ")(
201 po::value<std::vector<std::string>>()->multitoken(),
202 "Paramètres spécifiés sous forme de paires nom=valeur. "
203 "Peut être fourni plusieurs fois. Exemples :\n"
204 " -p solver.tol=1e-3\n"
205 " -p precond.coarse_enough=300");
208 po::store(po::parse_command_line(argc, argv, desc), vm);
211 if (vm.count(
"help")) {
213 std::cout << desc << std::endl;
218 if (vm.count(
"prm-file")) {
219 prm.read_json(vm[
"prm-file"].as<std::string>());
222 if (vm.count(
"prm")) {
223 for (
const std::string& v : vm[
"prm"].as<std::vector<std::string>>()) {
229 std::vector<ptrdiff_t> ptr;
230 std::vector<ptrdiff_t> col;
231 std::vector<double> val;
232 std::vector<double> rhs;
234 int block_size = vm[
"block-size"].as<
int>();
235 prm.put(
"precond.block_size", block_size);
238 if (vm[
"binary"].as<bool>()) {
239 n = read_binary(comm,
240 vm[
"matrix"].as<std::string>(),
241 vm[
"rhs"].as<std::string>(),
242 block_size, ptr, col, val, rhs);
245 n = read_matrix_market(comm,
246 vm[
"matrix"].as<std::string>(),
247 vm[
"rhs"].as<std::string>(),
248 block_size, ptr, col, val, rhs);
254 auto A = partition<Backend>(comm,
256 vm[
"partitioner"].as<Alina::eMatrixPartitionerType>(),
274 Solver solve(comm, A, prm);
278 std::cout << solve << std::endl;
280 std::vector<double> x(rhs.size(), 0.0);
286 if (comm.rank == 0) {
287 std::cout <<
"Itérations: " << r.nbIteration() << std::endl
288 <<
"Erreur: " << r.residual() << std::endl
289 << prof << std::endl;
Algebraic multigrid method.
Distributed CPR preconditioner.
Runtime wrapper for distributed direct solvers.
Distributed Matrix using message passing.
Iterative solver wrapper for distributed linear systems.
Classe pour stocker les paramètres sous forme d'arbre hiérarchique clé/valeur.
Matrix class, to be used by user.
Décrit un ensemble d'options en ligne de commande.
Stocke les valeurs d'options analysées.
-- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature --
Use a relaxation as a distributed preconditioner.
Alina::detail::empty_params params
Distributed memory sparse approximate inverse relaxation scheme.
Runtime-configurable wrapper around matrix partitioner.
Wrapper de commodité autour de MPI_Comm.