b2api
B2000++ API Reference Manual, VERSION 4.6
 
Loading...
Searching...
No Matches
b2vector_operation.H
1//------------------------------------------------------------------------
2// b2vector_operation.H --
3//
4// A framework for generic linear algebraic (matrix) computations.
5//
6// written by Mathias Doreille
7//
8// Copyright (c) 2004-2012 SMR Engineering & Development SA
9// 2502 Bienne, Switzerland
10//
11// All Rights Reserved. Proprietary source code. The contents of
12// this file may not be disclosed to third parties, copied or
13// duplicated in any form, in whole or in part, without the prior
14// written permission of SMR.
15//------------------------------------------------------------------------
16
17#ifndef __B2VECTOR_OPERATION_H__
18#define __B2VECTOR_OPERATION_H__
19
20#include "b2linear_algebra_def.H"
21
22namespace b2000 { namespace b2linalg {
23
24template <typename T1, typename T2>
25struct Sum {
26 typedef Sum const_base;
27};
28
29template <typename T, typename STORAGE1, typename STORAGE2>
30class Vector<T, Sum<STORAGE1, STORAGE2> > {
31public:
32 Vector(const Vector<T, STORAGE1>& v1_, const Vector<T, STORAGE2>& v2_, T scale_ = T(1))
33 : v1(v1_), v2(v2_), scale(scale_) {
34 if (v1.size() != v2.size()) {
35 Exception() << "The two vectors do not have the same size." << THROW;
36 }
37 }
38
39 size_t size() const { return v1.size(); }
40
41 const T& operator[](size_t i) const { return scale * (v1[i] + v2[i]); }
42
43 Vector& operator*(T t) {
44 scale *= t;
45 return *this;
46 }
47
48private:
49 Vector<T, STORAGE1> v1;
50 Vector<T, STORAGE2> v2;
51 T scale;
52 MVFRIEND;
53};
54
55template <typename T1, typename T2>
56struct MVProd {
57 typedef MVProd const_base;
58};
59
60template <typename T, typename STORAGE1, typename STORAGE2>
61class Vector<T, MVProd<STORAGE1, STORAGE2> > {
62public:
63 Vector(const Matrix<T, STORAGE1>& m_, const Vector<T, STORAGE2>& v_, T scale_ = T(1))
64 : m(m_), v(v_), scale(scale_) {
65 if (m.size2() != v.size()) {
66 Exception() << "The number of columns of the matrix (=" << m.size2()
67 << ") differ from the size of the vector (=" << v.size() << ")." << THROW;
68 }
69 }
70
71 size_t size() const { return m.size1(); }
72
73 T operator()(size_t i) const { return scale * transpose(m)[i] * v; }
74
75 Vector& operator*(T t) {
76 scale *= t;
77 return *this;
78 }
79
80private:
81 Matrix<T, STORAGE1> m;
82 Vector<T, STORAGE2> v;
83 T scale;
84 MVFRIEND;
85};
86
87template <typename T1, typename S1, typename T2, typename S2>
88inline void copy_v(const Vector<T1, S1>& a, Vector<T2, S2>& b) {
89 b.resize(a.size(), T2(0));
90 for (size_t i = 0; i != a.size(); ++i) { b[i] = a[i]; }
91}
92
93template <typename T, typename STORAGE1, typename STORAGE2>
94Vector<T, Sum<typename STORAGE1::const_base, typename STORAGE2::const_base> > operator+(
95 const Vector<T, STORAGE1>& v1, const Vector<T, STORAGE2>& v2) {
96 return Vector<T, Sum<typename STORAGE1::const_base, typename STORAGE2::const_base> >(v1, v2);
97}
98
99template <typename T, typename STORAGE1, typename STORAGE2>
100Vector<T, Sum<typename STORAGE1::const_base, typename STORAGE2::const_base> > operator-(
101 const Vector<T, STORAGE1>& v1, const Vector<T, STORAGE2>& v2) {
102 return Vector<T, Sum<typename STORAGE1::const_base, typename STORAGE2::const_base> >(v1, -v2);
103}
104
105template <typename T, typename STORAGE1, typename STORAGE2>
106T operator*(const Vector<T, STORAGE1>& v1, const Vector<T, STORAGE2>& v2) {
107 return Vector<T, typename STORAGE1::const_base>(v1)
108 * Vector<T, typename STORAGE2::const_base>(v2);
109}
110
111template <typename T, typename STORAGE1, typename STORAGE2>
112Vector<T, MVProd<typename STORAGE1::const_base, typename STORAGE2::const_base> > operator*(
113 const Matrix<T, STORAGE1>& m, const Vector<T, STORAGE2>& v) {
114 return Vector<T, MVProd<typename STORAGE1::const_base, typename STORAGE2::const_base> >(m, v);
115}
116
117template <typename T, typename STORAGE1, typename STORAGE2>
118Vector<T, MVProd<typename STORAGE1::const_base, typename STORAGE2::const_base> > operator*(
119 const Vector<T, STORAGE2>& v, const Matrix<T, STORAGE1>& m) {
120 return Vector<T, MVProd<typename STORAGE1::const_base, typename STORAGE2::const_base> >(
121 transposed(m), v);
122}
123
124template <typename T, typename STORAGE>
125Vector<T, typename STORAGE::const_base> operator*(T t, const Vector<T, STORAGE>& v) {
126 return Vector<T, typename STORAGE::const_base>(v) * t;
127}
128
129template <typename T, typename STORAGE>
130Vector<T, typename STORAGE::const_base> operator*(const Vector<T, STORAGE>& v, T t) {
131 return Vector<T, typename STORAGE::const_base>(v) * t;
132}
133
134template <typename T, typename STORAGE>
135Vector<T, typename STORAGE::const_base> operator-(const Vector<T, STORAGE>& v) {
136 return Vector<T, typename STORAGE::const_base>(v) * T(-1);
137}
138
139template <typename T, typename TYPE>
140std::ostream& operator<<(std::ostream& out, const Vector<T, TYPE>& v) {
141 out << "( ";
142 for (size_t i = 0; i != v.size(); ++i) { out << v[i] << ", "; }
143 out << ")";
144 return out;
145}
146
147template <typename T>
148void copy(const Vector<T, Vdense_constref>& v1, Vector<T, Vdense>& v2) {
149 v2 = v1;
150}
151
152template <typename T>
153void copy(const Vector<b2000::csda<T>, Vdense_constref>& v1, Vector<T, Vdense>& v2) {
154 v2.resize(v1.size());
155 for (size_t i = 0; i != v2.size(); ++i) { v2[i] = v1[i].real(); }
156}
157
158template <typename T>
159void copy(const Vector<std::complex<T>, Vdense_constref>& v1, Vector<T, Vdense>& v2) {
160 v2.resize(v1.size());
161 for (size_t i = 0; i != v2.size(); ++i) { v2[i] = v1[i].real(); }
162}
163
164template <typename T>
165void copy(const Vector<T, Vdense>& v1, Vector<T, Vdense>& v2) {
166 v2 = v1;
167}
168
169template <typename T>
170void copy(const Vector<T, Vdense>& v1, Vector<b2000::csda<T>, Vdense>& v2) {
171 v2.resize(v1.size());
172 for (size_t i = 0; i != v2.size(); ++i) { v2[i] = b2000::csda<T>(v1[i]); }
173}
174
175template <typename T>
176void copy(const Vector<T, Vdense>& v1, Vector<std::complex<T>, Vdense>& v2) {
177 v2.resize(v1.size());
178 for (size_t i = 0; i != v2.size(); ++i) { v2[i] = std::complex<T>(v1[i]); }
179}
180
181template <typename T>
182inline Vector<T, Vincrement_ref> real(std::vector<b2000::csda<T> >& v) {
183 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]), 2);
184}
185
186template <typename T>
187inline Vector<T, Vincrement_ref> real(std::vector<std::complex<T> >& v) {
188 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]), 2);
189}
190
191template <typename T>
192inline Vector<T, Vincrement_ref> imag(std::vector<b2000::csda<T> >& v) {
193 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]) + 1, 2);
194}
195
196template <typename T>
197inline Vector<T, Vincrement_ref> imag(std::vector<std::complex<T> >& v) {
198 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]) + 1, 2);
199}
200
201template <typename T>
202inline Vector<T, Vincrement_constref> real(const std::vector<b2000::csda<T> >& v) {
203 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]), 2);
204}
205
206template <typename T>
207inline Vector<T, Vincrement_constref> real(const std::vector<std::complex<T> >& v) {
208 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]), 2);
209}
210
211template <typename T>
212inline Vector<T, Vincrement_constref> imag(const std::vector<b2000::csda<T> >& v) {
213 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]) + 1, 2);
214}
215
216template <typename T>
217inline Vector<T, Vincrement_constref> imag(const std::vector<std::complex<T> >& v) {
218 return Vector<T, Vincrement_ref>(v.size(), reinterpret_cast<T*>(&v[0]) + 1, 2);
219}
220
221}} // namespace b2000::b2linalg
222
223#endif
#define THROW
Definition b2exception.H:198
Contains the base classes for implementing Finite Elements.
Definition b2boundary_condition.H:32