Distributed Ranges
Loading...
Searching...
No Matches
distributed_sparse_matrix.hpp
1// SPDX-FileCopyrightText: Intel Corporation
2//
3// SPDX-License-Identifier: BSD-3-Clause
4#pragma once
5#include <dr/detail/matrix_entry.hpp>
6#include <dr/mp/containers/matrix_formats/csr_eq_distribution.hpp>
7#include <dr/views/csr_matrix_view.hpp>
8
9namespace dr::mp {
10template <typename T>
11concept matrix_distibution = requires(T t, std::vector<int> res, int *input) {
12 { t.fence() } -> std::same_as<void>;
13 { t.segments() } -> rng::random_access_range;
14 { t.shape().first } -> std::convertible_to<std::size_t>;
15 { t.shape().second } -> std::convertible_to<std::size_t>;
16 { t.nnz() } -> std::same_as<std::size_t>;
17 { t.get_segment_from_offset(int()) } -> std::same_as<std::size_t>;
18 { t.get_id_in_segment(int()) } -> std::same_as<std::size_t>;
20 distribution());
21};
22
23template <typename T>
25 requires(T t, std::vector<typename T::elem_type> res, T::elem_type *input) {
26 t.local_gemv_and_collect(int(), res, input, 1);
27 };
28
29template <typename T, typename I, class BackendT = MpiBackend,
30 class MatrixDistrT = csr_eq_distribution<T, I, BackendT>>
33
34public:
36 using elem_type = T;
37 using index_type = I;
38 using key_type = dr::index<I>;
39 using size_type = std::size_t;
40 using difference_type = std::ptrdiff_t;
41 using backend_type = BackendT;
42
43 class iterator {
44 public:
45 using iterator_category = std::random_access_iterator_tag;
46 using value_type = typename distributed_sparse_matrix::value_type;
47 using difference_type = typename distributed_sparse_matrix::difference_type;
48
49 iterator() {}
50 iterator(const distributed_sparse_matrix *parent, difference_type offset)
51 : parent_(parent), offset_(offset) {}
52
53 auto operator+(difference_type n) const {
54 return iterator(parent_, offset_ + n);
55 }
56 friend auto operator+(difference_type n, const iterator &other) {
57 return other + n;
58 }
59 auto operator-(difference_type n) const {
60 return iterator(parent_, offset_ - n);
61 }
62 auto operator-(iterator other) const { return offset_ - other.offset_; }
63
64 auto &operator+=(difference_type n) {
65 offset_ += n;
66 return *this;
67 }
68 auto &operator-=(difference_type n) {
69 offset_ -= n;
70 return *this;
71 }
72 auto &operator++() {
73 offset_++;
74 return *this;
75 }
76 auto operator++(int) {
77 auto old = *this;
78 offset_++;
79 return old;
80 }
81 auto &operator--() {
82 offset_--;
83 return *this;
84 }
85 auto operator--(int) {
86 auto old = *this;
87 offset_--;
88 return old;
89 }
90
91 bool operator==(iterator other) const {
92 if (parent_ == nullptr || other.parent_ == nullptr) {
93 return false;
94 } else {
95 return offset_ == other.offset_;
96 }
97 }
98 auto operator<=>(iterator other) const {
99 assert(parent_ == other.parent_);
100 return offset_ <=> other.offset_;
101 }
102
103 auto operator*() const {
104 auto segment_id = parent_->distribution_.get_segment_from_offset(offset_);
105 auto id_in_segment = parent_->distribution_.get_id_in_segment(offset_);
106 return parent_->segments()[segment_id][id_in_segment];
107 }
108 auto operator[](difference_type n) const { return *(*this + n); }
109
110 auto local() {
111 auto segment_id = parent_->distribution_.get_segment_from_offset(offset_);
112 auto id_in_segment = parent_->distribution_.get_id_in_segment(offset_);
113 return (parent_->segments()[segment_id].begin() + id_in_segment).local();
114 }
115
116 auto segments() {
117 return dr::__detail::drop_segments(parent_->segments(), offset_);
118 }
119
120 private:
121 const distributed_sparse_matrix *parent_ = nullptr;
122 difference_type offset_;
123 };
124
127 operator=(const distributed_sparse_matrix &) = delete;
129
132 std::size_t root = 0,
133 distribution dist = distribution())
134 : distribution_(csr_view, dist, root) {}
135
137 auto begin() const { return iterator(this, 0); }
139 auto end() const { return begin() + distribution_.nnz(); }
140
142 auto size() const { return distribution_.nnz(); }
143
144 auto shape() const { return distribution_.shape(); }
146 auto operator[](difference_type n) const { return *(begin() + n); }
147 // auto &halo() const { return *halo_; } TODO
148
149 auto segments() const { return distribution_.segments(); }
150
151 void fence() { distribution_.fence(); }
152
153 template <typename C>
154 requires(vector_multiplicable<MatrixDistrT>)
155 auto local_gemv_and_collect(std::size_t root, C &res, T *vals,
156 std::size_t val_width) const {
157 distribution_.local_gemv_and_collect(root, res, vals, val_width);
158 }
159
160private:
161 MatrixDistrT distribution_;
162};
163} // namespace dr::mp
Definition: matrix_entry.hpp:20
Definition: distributed_vector.hpp:14
Definition: csr_eq_distribution.hpp:13
Definition: distributed_sparse_matrix.hpp:43
Definition: distributed_sparse_matrix.hpp:32
auto size() const
Returns size.
Definition: distributed_sparse_matrix.hpp:142
auto end() const
Returns iterator to end.
Definition: distributed_sparse_matrix.hpp:139
distributed_sparse_matrix(dr::views::csr_matrix_view< T, I > csr_view, std::size_t root=0, distribution dist=distribution())
Constructor.
Definition: distributed_sparse_matrix.hpp:131
auto operator[](difference_type n) const
Returns reference using index.
Definition: distributed_sparse_matrix.hpp:146
auto begin() const
Returns iterator to beginning.
Definition: distributed_sparse_matrix.hpp:137
Definition: csr_matrix_view.hpp:126
Definition: distributed_sparse_matrix.hpp:11
Definition: distributed_sparse_matrix.hpp:24
Definition: distribution.hpp:11