Skip to content

Commit 7d2dee7

Browse files
committed
linalg : hermitian_matrix_rank_2k_updateを追加 (#1233)
Signed-off-by: Yuya Asano <64895419+sukeya@users.noreply.github.com>
1 parent 42e737a commit 7d2dee7

File tree

2 files changed

+208
-1
lines changed

2 files changed

+208
-1
lines changed

reference/linalg.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,7 @@ BLAS 1, 2, 3のアルゴリズムでテンプレートパラメータが特に
107107
| [`symmetric_matrix_rank_k_update`](linalg/symmetric_matrix_rank_k_update.md) | xSYRK: 対称行列のRank-k更新 (function template) | C++26 |
108108
| [`hermitian_matrix_rank_k_update`](linalg/hermitian_matrix_rank_k_update.md) | xHERK: ハミルトニアン行列のRank-k更新 (function template) | C++26 |
109109
| [`symmetric_matrix_rank_2k_update`](linalg/symmetric_matrix_rank_2k_update.md) | xSYR2K: 対称行列のRank-2k更新 (function template) | C++26 |
110-
| `hermitian_matrix_rank_2k_update` | xHER2K: ハミルトニアン行列のRank-2k更新 (function template) | C++26 |
110+
| [`hermitian_matrix_rank_2k_update`](linalg/hermitian_matrix_rank_2k_update.md) | xHER2K: ハミルトニアン行列のRank-2k更新 (function template) | C++26 |
111111
| `triangular_matrix_matrix_left_solve` | xTRSM: 三角行列の連立一次方程式を解く (function template) | C++26 |
112112
| `triangular_matrix_matrix_right_solve` | xTRSM: 三角行列の連立一次方程式を解く (function template) | C++26 |
113113

Lines changed: 207 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,207 @@
1+
# hermitian_matrix_rank_2k_update
2+
3+
4+
* [mathjax enable]
5+
* linalg[meta header]
6+
* function template[meta id-type]
7+
* std::linalg[meta namespace]
8+
* cpp26[meta cpp]
9+
10+
11+
```cpp
12+
namespace std::linalg {
13+
template<in-matrix InMat1,
14+
in-matrix InMat2,
15+
possibly-packed-inout-matrix InOutMat,
16+
class Triangle>
17+
void hermitian_matrix_rank_2k_update(
18+
InMat1 A,
19+
InMat2 B,
20+
InOutMat C,
21+
Triangle t); // (1)
22+
23+
template<class ExecutionPolicy,
24+
in-matrix InMat1,
25+
in-matrix InMat2,
26+
possibly-packed-inout-matrix InOutMat,
27+
class Triangle>
28+
void hermitian_matrix_rank_2k_update(
29+
ExecutionPolicy&& exec,
30+
InMat1 A,
31+
InMat2 B,
32+
InOutMat C,
33+
Triangle t); // (2)
34+
}
35+
```
36+
37+
38+
## 概要
39+
エルミートな(対称かつ共役を取る)rank-2k updateを対称行列に行う。
40+
引数`t`は対称行列の成分が上三角にあるのか、それとも下三角にあるのかを示す。
41+
42+
- (1): $C \leftarrow C + AB^* + BA^*$
43+
- (2): (1)を指定された実行ポリシーで実行する。
44+
45+
46+
## 適格要件
47+
- 共通:
48+
+ `Triangle`は[`upper_triangle_t`](upper_triangle_t.md)または[`lower_triangle_t`](lower_triangle_t.md)
49+
+ `InMat`が[`layout_blas_packed`](layout_blas_packed.md)を持つなら、レイアウトの`Triangle`テンプレート引数とこの関数の`Triangle`テンプレート引数が同じ型
50+
+ [`possibly-addable`](possibly-addable.md)`<decltype(A), decltype(B), decltype(C)>()`が`true`
51+
+ [`compatible-static-extents`](compatible-static-extents.md)`<decltype(A), decltype(A)>(0, 1)`が`true` (つまり`A`が正方行列であること)
52+
- (2): [`is_execution_policy`](/reference/execution/is_execution_policy.md)`<ExecutionPolicy>::value`が`true`
53+
54+
55+
## 事前条件
56+
- `A.extent(0) == A.extent(1)`
57+
- [`addable`](addable.md)`(A, B, C)`が`true`
58+
59+
60+
## 効果
61+
$C \leftarrow C + AB^* + BA^*$
62+
63+
64+
## 戻り値
65+
なし
66+
67+
68+
## 計算量
69+
$O(\verb|A.extent(0)| \times \verb|A.extent(1)| \times \verb|C.extent(0)|)$
70+
71+
72+
## 例
73+
**[注意] 処理系にあるコンパイラで確認していないため、間違っているかもしれません。**
74+
75+
```cpp example
76+
#include <array>
77+
#include <iostream>
78+
#include <linalg>
79+
#include <mdspan>
80+
#include <vector>
81+
82+
template <class Matrix>
83+
void print_mat(const Matrix& A) {
84+
for(int i = 0; i < A.extent(0); ++i) {
85+
for(int j = 0; j < i; ++j) {
86+
std::cout << A[j, i] << ' ';
87+
}
88+
for(int j = i; j < A.extent(1) - 1; ++j) {
89+
std::cout << A[i, j] << ' ';
90+
}
91+
std::cout << A[i, A.extent(1) - 1] << '\n';
92+
}
93+
}
94+
95+
template <class Matrix>
96+
void init_mat(Matrix& A, double geta = 0.0) {
97+
for(int i = 0; i < A.extent(0); ++i) {
98+
for(int j = 0; j < A.extent(1); ++j) {
99+
A[i,j] = std::complex<double>(i + geta, j + geta);
100+
}
101+
}
102+
}
103+
104+
template <class Matrix>
105+
void init_herm_mat(Matrix& A) {
106+
for(int i = 0; i < A.extent(0); ++i) {
107+
A[i, i] = std::complex<double>(i, 0);
108+
for(int j = i + 1; j < A.extent(1); ++j) {
109+
A[i, j] = std::complex<double>(i, j);
110+
}
111+
}
112+
}
113+
114+
int main()
115+
{
116+
constexpr size_t N = 2;
117+
118+
using Scalar = std::complex<double>;
119+
using Vector = std::vector<Scalar>;
120+
using HermitianMatrix = std::mdspan<
121+
Scalar,
122+
std::extents<size_t, N, N>,
123+
std::linalg::layout_blas_packed<
124+
std::linalg::upper_triangle_t,
125+
std::linalg::row_major_t>
126+
>;
127+
128+
Vector A_vec(N * N);
129+
Vector B_vec(N * N);
130+
Vector C_vec(N * N);
131+
132+
std::mdspan A(A_vec.data());
133+
std::mdspan B(B_vec.data());
134+
HermitianMatrix C(C_vec.data());
135+
136+
init_mat(A);
137+
init_mat(B, 1);
138+
init_herm_mat(C);
139+
140+
// (1)
141+
std::cout << "(1)\n";
142+
std::linalg::hermitian_matrix_rank_2k_update(
143+
A,
144+
B,
145+
C,
146+
std::linalg::upper_triangle);
147+
print_mat(C);
148+
149+
// (2)
150+
init_herm_mat(C);
151+
std::cout << "(2)\n";
152+
std::linalg::hermitian_matrix_rank_2k_update(
153+
std::execution::par,
154+
A,
155+
B,
156+
C,
157+
std::linalg::upper_triangle);
158+
print_mat(C);
159+
160+
return 0;
161+
}
162+
```
163+
* A.extent[link /reference/mdspan/extents/extent.md]
164+
* std::complex[link /reference/complex/complex.md]
165+
* std::mdspan[link /reference/mdspan/mdspan.md]
166+
* std::extents[link /reference/mdspan/extents.md]
167+
* std::linalg::layout_blas_packed[link /reference/linalg/layout_blas_packed.md]
168+
* std::linalg::upper_triangle_t[link /reference/linalg/upper_triangle_t.md]
169+
* std::linalg::row_major_t[link /reference/linalg/row_major_t.md]
170+
* std::linalg::upper_triangle[link /reference/linalg/upper_triangle_t.md]
171+
* std::execution::par[link /reference/execution/execution/execution_policy.md]
172+
* std::linalg::hermitian_matrix_rank_2k_update[color ff0000]
173+
174+
175+
### 出力
176+
```
177+
(1)
178+
(4,0) (6,4)
179+
(6,-4) (13,0)
180+
(2)
181+
(4,0) (6,4)
182+
(6,-4) (13,0)
183+
```
184+
185+
186+
## バージョン
187+
### 言語
188+
- C++26
189+
190+
### 処理系
191+
- [Clang](/implementation.md#clang): ??
192+
- [GCC](/implementation.md#gcc): ??
193+
- [ICC](/implementation.md#icc): ??
194+
- [Visual C++](/implementation.md#visual_cpp): ??
195+
196+
197+
## 関連項目
198+
- [`execution`](/reference/execution.md)
199+
- [`mdspan`](/reference/mdspan.md)
200+
- [`upper_triangle_t`](upper_triangle_t.md)
201+
- [`lower_triangle_t`](lower_triangle_t.md)
202+
203+
204+
## 参照
205+
- [P1673R13 A free function linear algebra interface based on the BLAS](https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2023/p1673r13.html)
206+
- [LAPACK: {he,sy}r2k: Hermitian/symmetric rank-2k update](https://netlib.org/lapack/explore-html/d8/d94/group__her2k.html)
207+

0 commit comments

Comments
 (0)