Warning: this documentation for the development version is under construction.
00001 // Copyright (C) 2003-2009 Marc Duruflé 00002 // Copyright (C) 2001-2009 Vivien Mallet 00003 // Copyright (C) 2010 INRIA 00004 // Author(s): Marc Fragu 00005 // 00006 // This file is part of the linear-algebra library Seldon, 00007 // http://seldon.sourceforge.net/. 00008 // 00009 // Seldon is free software; you can redistribute it and/or modify it under the 00010 // terms of the GNU Lesser General Public License as published by the Free 00011 // Software Foundation; either version 2.1 of the License, or (at your option) 00012 // any later version. 00013 // 00014 // Seldon is distributed in the hope that it will be useful, but WITHOUT ANY 00015 // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 00016 // FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for 00017 // more details. 00018 // 00019 // You should have received a copy of the GNU Lesser General Public License 00020 // along with Seldon. If not, see http://www.gnu.org/licenses/. 00021 00022 00023 #ifndef SELDON_FILE_FUNCTIONS_VECTOR_CXX 00024 #define SELDON_FILE_FUNCTIONS_VECTOR_CXX 00025 00026 00027 #include "Functions_Vector.hxx" 00028 00029 00030 /* 00031 Functions defined in this file: 00032 00033 alpha X -> X 00034 Mlt(alpha, X) 00035 00036 alpha X + Y -> Y 00037 Add(alpha, X, Y) 00038 00039 X -> Y 00040 Copy(X, Y) 00041 00042 X <-> Y 00043 Swap(X, Y) 00044 00045 X.Y 00046 DotProd(X, Y) 00047 DotProdConj(X, Y) 00048 00049 ||X|| 00050 Norm1(X) 00051 Norm2(X) 00052 GetMaxAbsIndex(X) 00053 00054 Omega X 00055 GenRot(x, y, cos, sin) 00056 ApplyRot(x, y, cos, sin) 00057 00058 */ 00059 00060 00061 namespace Seldon 00062 { 00063 00064 00066 // MLT // 00067 00068 00069 template <class T0, 00070 class T1, class Storage1, class Allocator1> 00071 void Mlt(const T0 alpha, Vector<T1, Storage1, Allocator1>& X) 00072 { 00073 X *= alpha; 00074 } 00075 00076 00077 // MLT // 00079 00080 00082 // ADD // 00083 00084 00085 template <class T0, 00086 class T1, class Storage1, class Allocator1, 00087 class T2, class Storage2, class Allocator2> 00088 void Add(const T0 alpha, 00089 const Vector<T1, Storage1, Allocator1>& X, 00090 Vector<T2, Storage2, Allocator2>& Y) 00091 { 00092 if (alpha != T0(0)) 00093 { 00094 T1 alpha_ = alpha; 00095 00096 int ma = X.GetM(); 00097 00098 #ifdef SELDON_CHECK_DIMENSIONS 00099 CheckDim(X, Y, "Add(alpha, X, Y)"); 00100 #endif 00101 00102 for (int i = 0; i < ma; i++) 00103 Y(i) += alpha_ * X(i); 00104 } 00105 } 00106 00107 00108 template <class T0, 00109 class T1, class Allocator1, 00110 class T2, class Allocator2> 00111 void Add(const T0 alpha, 00112 const Vector<T1, PETScSeq, Allocator1>& X, 00113 Vector<T2, PETScSeq, Allocator2>& Y) 00114 { 00115 if (alpha != T0(0)) 00116 { 00117 T1 alpha_ = alpha; 00118 00119 int ma = X.GetM(); 00120 00121 #ifdef SELDON_CHECK_DIMENSIONS 00122 CheckDim(X, Y, "Add(alpha, X, Y)"); 00123 #endif 00124 00125 VecAXPY(Y.GetPetscVector(), alpha_, X.GetPetscVector()); 00126 } 00127 } 00128 00129 00130 template <class T0, 00131 class T1, class Allocator1, 00132 class T2, class Allocator2> 00133 void Add(const T0 alpha, 00134 const Vector<T1, PETScPar, Allocator1>& X, 00135 Vector<T2, PETScPar, Allocator2>& Y) 00136 { 00137 if (alpha != T0(0)) 00138 { 00139 T1 alpha_ = alpha; 00140 00141 int ma = X.GetM(); 00142 00143 #ifdef SELDON_CHECK_DIMENSIONS 00144 CheckDim(X, Y, "Add(alpha, X, Y)"); 00145 #endif 00146 00147 VecAXPY(Y.GetPetscVector(), alpha_, X.GetPetscVector()); 00148 } 00149 } 00150 00151 00152 00153 template <class T0, 00154 class T1, class Allocator1, 00155 class T2, class Allocator2> 00156 void Add(const T0 alpha, 00157 const Vector<T1, VectSparse, Allocator1>& X, 00158 Vector<T2, VectSparse, Allocator2>& Y) 00159 { 00160 if (alpha != T0(0)) 00161 { 00162 Vector<T1, VectSparse, Allocator1> Xalpha = X; 00163 Xalpha *= alpha; 00164 Y.AddInteractionRow(Xalpha.GetSize(), 00165 Xalpha.GetIndex(), Xalpha.GetData(), true); 00166 } 00167 } 00168 00169 00170 template <class T0, 00171 class T1, class Allocator1, 00172 class T2, class Allocator2> 00173 void Add(const T0 alpha, 00174 const Vector<T1, Collection, Allocator1>& X, 00175 Vector<T2, Collection, Allocator2>& Y) 00176 { 00177 00178 #ifdef SELDON_CHECK_DIMENSIONS 00179 CheckDim(X, Y, "Add(X, Y)", "X + Y"); 00180 #endif 00181 00182 for (int i = 0; i < X.GetNvector(); i++) 00183 Add(alpha, X.GetVector(i), Y.GetVector(i)); 00184 } 00185 00186 00187 template <class T0, 00188 class T1, template <class U1> class Allocator1, 00189 class T2, template <class U2> class Allocator2> 00190 void Add(const T0 alpha, 00191 const 00192 Vector<FloatDouble, DenseSparseCollection, Allocator1<T1> >& X, 00193 Vector<FloatDouble, DenseSparseCollection, Allocator2<T2> >& Y) 00194 { 00195 00196 #ifdef SELDON_CHECK_DIMENSIONS 00197 CheckDim(X, Y, "Add(X, Y)"); 00198 #endif 00199 00200 Add(alpha, X.GetFloatDense(), Y.GetFloatDense()); 00201 Add(alpha, X.GetFloatSparse(), Y.GetFloatSparse()); 00202 Add(alpha, X.GetDoubleDense(), Y.GetDoubleDense()); 00203 Add(alpha, X.GetDoubleSparse(), Y.GetDoubleSparse()); 00204 } 00205 00206 00207 template <class T0, 00208 class T1, template <class U1> class Allocator1, 00209 class T2, class Storage2, class Allocator2> 00210 void Add(const T0 alpha, 00211 const 00212 Vector<FloatDouble, DenseSparseCollection, Allocator1<T1> >& X, 00213 Vector<T2, Storage2, Allocator2>& Y) 00214 { 00215 if (alpha != T0(0)) 00216 { 00217 double alpha_ = alpha; 00218 00219 int ma = X.GetM(); 00220 00221 #ifdef SELDON_CHECK_DIMENSIONS 00222 CheckDim(X, Y, "Add(alpha, X, Y)"); 00223 #endif 00224 00225 for (int i = 0; i < ma; i++) 00226 Y(i) += alpha_ * X(i); 00227 00228 } 00229 } 00230 00231 00232 // ADD // 00234 00235 00237 // COPY // 00238 00239 00240 template <class T1, class Storage1, class Allocator1, 00241 class T2, class Storage2, class Allocator2> 00242 void Copy(const Vector<T1, Storage1, Allocator1>& X, 00243 Vector<T2, Storage2, Allocator2>& Y) 00244 { 00245 Y.Copy(X); 00246 } 00247 00248 00249 template <class T1, class Allocator1, 00250 class T2, class Allocator2> 00251 void Copy(const Vector<T1, Collection, Allocator1>& X, 00252 Vector<T2, VectFull, Allocator2>& Y) 00253 { 00254 Y.Clear(); 00255 for (int i = 0; i < X.GetNvector(); i++) 00256 Y.PushBack(X.GetVector(i)); 00257 } 00258 00259 00260 template<class T, class Alloc1, class Alloc2> 00261 void Copy(const Vector<T, PETScPar, Alloc1>& A, 00262 Vector<T, VectFull, Alloc2>& B) 00263 { 00264 B.Reallocate(A.GetLocalM()); 00265 T *local_data; 00266 VecGetArray(A.GetPetscVector(), &local_data); 00267 for (int i = 0; i < A.GetLocalM(); i++) 00268 B(i) = local_data[i]; 00269 VecRestoreArray(A.GetPetscVector(), &local_data); 00270 } 00271 00272 00273 template<class T, class Alloc1, class Alloc2> 00274 void Copy(const Vector<T, VectFull, Alloc1>& A, 00275 Vector<T, PETScPar, Alloc2>& B) 00276 { 00277 T *local_data; 00278 VecGetArray(B.GetPetscVector(), &local_data); 00279 for (int i = 0; i < A.GetM(); i++) 00280 local_data[i] = A(i); 00281 VecRestoreArray(B.GetPetscVector(), &local_data); 00282 } 00283 00284 00285 00286 // COPY // 00288 00289 00291 // SWAP // 00292 00293 00294 template <class T, class Storage, class Allocator> 00295 void Swap(Vector<T, Storage, Allocator>& X, 00296 Vector<T, Storage, Allocator>& Y) 00297 { 00298 int nx = X.GetM(); 00299 T* data = X.GetData(); 00300 X.Nullify(); 00301 X.SetData(Y.GetM(), Y.GetData()); 00302 Y.Nullify(); 00303 Y.SetData(nx, data); 00304 } 00305 00306 00307 template <class T, class Allocator> 00308 void Swap(Vector<T, VectSparse, Allocator>& X, 00309 Vector<T, VectSparse, Allocator>& Y) 00310 { 00311 int nx = X.GetM(); 00312 T* data = X.GetData(); 00313 int* index = X.GetIndex(); 00314 X.Nullify(); 00315 X.SetData(Y.GetM(), Y.GetData(), Y.GetIndex()); 00316 Y.Nullify(); 00317 Y.SetData(nx, data, index); 00318 } 00319 00320 00321 // SWAP // 00323 00324 00326 // DOTPROD // 00327 00328 00330 template<class T1, class Storage1, class Allocator1, 00331 class T2, class Storage2, class Allocator2> 00332 T1 DotProd(const Vector<T1, Storage1, Allocator1>& X, 00333 const Vector<T2, Storage2, Allocator2>& Y) 00334 { 00335 T1 value; 00336 SetComplexZero(value); 00337 00338 #ifdef SELDON_CHECK_DIMENSIONS 00339 CheckDim(X, Y, "DotProd(X, Y)"); 00340 #endif 00341 00342 for (int i = 0; i < X.GetM(); i++) 00343 value += X(i) * Y(i); 00344 00345 return value; 00346 } 00347 00348 00350 template<class T1, class Allocator1, 00351 class T2, class Allocator2> 00352 typename T1::value_type DotProd(const Vector<T1, Collection, Allocator1>& X, 00353 const Vector<T2, Collection, Allocator2>& Y) 00354 { 00355 typename T1::value_type value(0); 00356 00357 #ifdef SELDON_CHECK_DIMENSIONS 00358 CheckDim(X, Y, "DotProd(X, Y)", "<X, Y>"); 00359 #endif 00360 00361 for (int i = 0; i < X.GetNvector(); i++) 00362 value += DotProd(X.GetVector(i), Y.GetVector(i)); 00363 return value; 00364 } 00365 00366 00368 template<class T1, template <class U1> class Allocator1, 00369 class T2, template <class U2> class Allocator2> 00370 double 00371 DotProd(const 00372 Vector<FloatDouble, DenseSparseCollection, Allocator1<T1> >& X, 00373 const 00374 Vector<FloatDouble, DenseSparseCollection, Allocator2<T2> >& Y) 00375 { 00376 00377 #ifdef SELDON_CHECK_DIMENSIONS 00378 CheckDim(X, Y, "DotProd(X, Y)"); 00379 #endif 00380 00381 double value(0.); 00382 value += DotProd(X.GetFloatDense(), Y.GetFloatDense()); 00383 value += DotProd(X.GetFloatSparse(), Y.GetFloatSparse()); 00384 value += DotProd(X.GetDoubleDense(), Y.GetDoubleDense()); 00385 value += DotProd(X.GetDoubleSparse(), Y.GetDoubleSparse()); 00386 return value; 00387 } 00388 00389 00391 template<class T1, class Storage1, class Allocator1, 00392 class T2, class Storage2, class Allocator2> 00393 T1 DotProdConj(const Vector<T1, Storage1, Allocator1>& X, 00394 const Vector<T2, Storage2, Allocator2>& Y) 00395 { 00396 return DotProd(X, Y); 00397 } 00398 00399 00401 template<class T1, class Storage1, class Allocator1, 00402 class T2, class Storage2, class Allocator2> 00403 complex<T1> DotProdConj(const Vector<complex<T1>, Storage1, Allocator1>& X, 00404 const Vector<T2, Storage2, Allocator2>& Y) 00405 { 00406 complex<T1> value; 00407 SetComplexZero(value); 00408 00409 #ifdef SELDON_CHECK_DIMENSIONS 00410 CheckDim(X, Y, "DotProdConj(X, Y)"); 00411 #endif 00412 00413 for (int i = 0; i < X.GetM(); i++) 00414 value += conj(X(i)) * Y(i); 00415 00416 return value; 00417 } 00418 00419 00421 template<class T1, class Allocator1, 00422 class T2, class Allocator2> 00423 T1 DotProd(const Vector<T1, VectSparse, Allocator1>& X, 00424 const Vector<T2, VectSparse, Allocator2>& Y) 00425 { 00426 T1 value; 00427 SetComplexZero(value); 00428 00429 int size_x = X.GetSize(); 00430 int size_y = Y.GetSize(); 00431 int kx = 0, ky = 0, pos_x; 00432 while (kx < size_x) 00433 { 00434 pos_x = X.Index(kx); 00435 while (ky < size_y && Y.Index(ky) < pos_x) 00436 ky++; 00437 00438 if (ky < size_y && Y.Index(ky) == pos_x) 00439 value += X.Value(kx) * Y.Value(ky); 00440 00441 kx++; 00442 } 00443 00444 return value; 00445 } 00446 00447 00449 template<class T1, class Allocator1, 00450 class T2, class Allocator2> 00451 complex<T1> 00452 DotProdConj(const Vector<complex<T1>, VectSparse, Allocator1>& X, 00453 const Vector<T2, VectSparse, Allocator2>& Y) 00454 { 00455 complex<T1> value(0, 0); 00456 00457 int size_x = X.GetSize(); 00458 int size_y = Y.GetSize(); 00459 int kx = 0, ky = 0, pos_x; 00460 while (kx < size_x) 00461 { 00462 pos_x = X.Index(kx); 00463 while (ky < size_y && Y.Index(ky) < pos_x) 00464 ky++; 00465 00466 if (ky < size_y && Y.Index(ky) == pos_x) 00467 value += conj(X.Value(kx)) * Y.Value(ky); 00468 00469 kx++; 00470 } 00471 00472 return value; 00473 } 00474 00475 00476 // DOTPROD // 00478 00479 00481 // NORM1 // 00482 00483 00484 template<class T1, class Storage1, class Allocator1> 00485 T1 Norm1(const Vector<T1, Storage1, Allocator1>& X) 00486 { 00487 T1 value(0); 00488 00489 for (int i = 0; i < X.GetM(); i++) 00490 value += abs(X(i)); 00491 00492 return value; 00493 } 00494 00495 00496 template<class T1, class Storage1, class Allocator1> 00497 T1 Norm1(const Vector<complex<T1>, Storage1, Allocator1>& X) 00498 { 00499 T1 value(0); 00500 00501 for (int i = 0; i < X.GetM(); i++) 00502 value += abs(X(i)); 00503 00504 return value; 00505 } 00506 00507 00508 template<class T1, class Allocator1> 00509 T1 Norm1(const Vector<T1, VectSparse, Allocator1>& X) 00510 { 00511 T1 value(0); 00512 00513 for (int i = 0; i < X.GetSize(); i++) 00514 value += abs(X.Value(i)); 00515 00516 return value; 00517 } 00518 00519 00520 template<class T1, class Allocator1> 00521 T1 Norm1(const Vector<complex<T1>, VectSparse, Allocator1>& X) 00522 { 00523 T1 value(0); 00524 00525 for (int i = 0; i < X.GetSize(); i++) 00526 value += abs(X.Value(i)); 00527 00528 return value; 00529 } 00530 00531 00532 // NORM1 // 00534 00535 00537 // NORM2 // 00538 00539 00540 template<class T1, class Storage1, class Allocator1> 00541 T1 Norm2(const Vector<T1, Storage1, Allocator1>& X) 00542 { 00543 T1 value(0); 00544 00545 for (int i = 0; i < X.GetM(); i++) 00546 value += X(i) * X(i); 00547 00548 return sqrt(value); 00549 } 00550 00551 00552 template<class T1, class Storage1, class Allocator1> 00553 T1 Norm2(const Vector<complex<T1>, Storage1, Allocator1>& X) 00554 { 00555 T1 value(0); 00556 00557 for (int i = 0; i < X.GetM(); i++) 00558 value += real(X(i) * conj(X(i))); 00559 00560 return sqrt(value); 00561 } 00562 00563 00564 template<class T1, class Allocator1> 00565 T1 Norm2(const Vector<T1, VectSparse, Allocator1>& X) 00566 { 00567 T1 value(0); 00568 00569 for (int i = 0; i < X.GetSize(); i++) 00570 value += X.Value(i) * X.Value(i); 00571 00572 return sqrt(value); 00573 } 00574 00575 00576 template<class T1, class Allocator1> 00577 T1 Norm2(const Vector<complex<T1>, VectSparse, Allocator1>& X) 00578 { 00579 T1 value(0); 00580 00581 for (int i = 0; i < X.GetSize(); i++) 00582 value += real(X.Value(i) * conj(X.Value(i))); 00583 00584 return sqrt(value); 00585 } 00586 00587 00588 // NORM2 // 00590 00591 00593 // GETMAXABSINDEX // 00594 00595 00596 template<class T, class Storage, class Allocator> 00597 int GetMaxAbsIndex(const Vector<T, Storage, Allocator>& X) 00598 { 00599 return X.GetNormInfIndex(); 00600 } 00601 00602 00603 // GETMAXABSINDEX // 00605 00606 00608 // APPLYROT // 00609 00610 00612 template<class T> 00613 void GenRot(T& a_in, T& b_in, T& c_, T& s_) 00614 { 00615 // Old BLAS version. 00616 T roe; 00617 if (abs(a_in) > abs(b_in)) 00618 roe = a_in; 00619 else 00620 roe = b_in; 00621 00622 T scal = abs(a_in) + abs(b_in); 00623 T r, z; 00624 if (scal != T(0)) 00625 { 00626 T a_scl = a_in / scal; 00627 T b_scl = b_in / scal; 00628 r = scal * sqrt(a_scl * a_scl + b_scl * b_scl); 00629 if (roe < T(0)) 00630 r *= T(-1); 00631 00632 c_ = a_in / r; 00633 s_ = b_in / r; 00634 z = T(1); 00635 if (abs(a_in) > abs(b_in)) 00636 z = s_; 00637 else if (abs(b_in) >= abs(a_in) && c_ != T(0)) 00638 z = T(1) / c_; 00639 } 00640 else 00641 { 00642 c_ = T(1); 00643 s_ = T(0); 00644 r = T(0); 00645 z = T(0); 00646 } 00647 a_in = r; 00648 b_in = z; 00649 } 00650 00651 00653 template<class T> 00654 void GenRot(complex<T>& a_in, complex<T>& b_in, T& c_, complex<T>& s_) 00655 { 00656 00657 T a = abs(a_in), b = abs(b_in); 00658 if (a == T(0)) 00659 { 00660 c_ = T(0); 00661 s_ = complex<T>(1, 0); 00662 a_in = b_in; 00663 } 00664 else 00665 { 00666 T scale = a + b; 00667 T a_scal = abs(a_in / scale); 00668 T b_scal = abs(b_in / scale); 00669 T norm = sqrt(a_scal * a_scal + b_scal * b_scal) * scale; 00670 00671 c_ = a / norm; 00672 complex<T> alpha = a_in / a; 00673 s_ = alpha * conj(b_in) / norm; 00674 a_in = alpha * norm; 00675 } 00676 b_in = complex<T>(0, 0); 00677 } 00678 00679 00681 template<class T> 00682 void ApplyRot(T& x, T& y, const T c_, const T s_) 00683 { 00684 T temp = c_ * x + s_ * y; 00685 y = c_ * y - s_ * x; 00686 x = temp; 00687 } 00688 00689 00691 template<class T> 00692 void ApplyRot(complex<T>& x, complex<T>& y, 00693 const T& c_, const complex<T>& s_) 00694 { 00695 complex<T> temp = s_ * y + c_ * x; 00696 y = -conj(s_) * x + c_ * y; 00697 x = temp; 00698 } 00699 00700 00701 // APPLYROT // 00703 00704 00706 // CHECKDIM // 00707 00708 00710 00720 template <class T0, class Storage0, class Allocator0, 00721 class T1, class Storage1, class Allocator1> 00722 void CheckDim(const Vector<T0, Storage0, Allocator0>& X, 00723 const Vector<T1, Storage1, Allocator1>& Y, 00724 string function, string op) 00725 { 00726 if (X.GetLength() != Y.GetLength()) 00727 throw WrongDim(function, string("Operation ") + op 00728 + string(" not permitted:") 00729 + string("\n X (") + to_str(&X) + string(") is a ") 00730 + string("vector of length ") + to_str(X.GetLength()) 00731 + string(";\n Y (") + to_str(&Y) + string(") is a ") 00732 + string("vector of length ") + to_str(Y.GetLength()) 00733 + string(".")); 00734 } 00735 00736 00738 00748 template <class T0, class Allocator0, 00749 class T1, class Allocator1> 00750 void CheckDim(const Vector<T0, Vect_Sparse, Allocator0>& X, 00751 const Vector<T1, Vect_Sparse, Allocator1>& Y, 00752 string function, string op) 00753 { 00754 // The dimension of a Vector<Vect_Sparse> is infinite, 00755 // so no vector dimension checking has to be done. 00756 } 00757 00758 00760 00770 template <class T0, class Allocator0, 00771 class T1, class Allocator1> 00772 void CheckDim(const Vector<T0, Collection, Allocator0>& X, 00773 const Vector<T1, Collection, Allocator1>& Y, 00774 string function, string op) 00775 { 00776 if (X.GetLength() != Y.GetLength()) 00777 throw WrongDim(function, string("Operation ") + op 00778 + string(" not permitted:") 00779 + string("\n X (") + to_str(&X) + string(") is a ") 00780 + string("vector of length ") + to_str(X.GetLength()) 00781 + string(";\n Y (") + to_str(&Y) + string(") is a ") 00782 + string("vector of length ") + to_str(Y.GetLength()) 00783 + string(".")); 00784 00785 if (X.GetNvector() != Y.GetNvector()) 00786 throw WrongDim(function, string("Operation ") + op 00787 + string(" not permitted:") 00788 + string("\n X (") + to_str(&X) + string(") is a ") 00789 + string("vector of length ") + to_str(X.GetNvector()) 00790 + string(";\n Y (") + to_str(&Y) + string(") is a ") 00791 + string("vector of length ") + to_str(Y.GetNvector()) 00792 + string(".")); 00793 } 00794 00795 00797 00807 template <class T0, class Allocator0, class Allocator00, 00808 class T1, class Allocator1, class Allocator11> 00809 void CheckDim(const Vector<Vector<T0, Vect_Sparse, Allocator0>, 00810 Collection, Allocator00>& X, 00811 const Vector<Vector<T1, Vect_Sparse, Allocator1>, 00812 Collection, Allocator11>& Y, 00813 string function, string op) 00814 { 00815 if (X.GetNvector() != Y.GetNvector()) 00816 throw WrongDim(function, string("Operation ") + op 00817 + string(" not permitted:") 00818 + string("\n X (") + to_str(&X) + string(") is a ") 00819 + string("vector of length ") + to_str(X.GetNvector()) 00820 + string(";\n Y (") + to_str(&Y) + string(") is a ") 00821 + string("vector of length ") + to_str(Y.GetNvector()) 00822 + string(".")); 00823 } 00824 00825 00827 00837 template <class T0, class Allocator0, 00838 class T1, class Allocator1> 00839 void CheckDim(const Vector<T0, VectFull, Allocator0>& X, 00840 Vector<T1, Collection, Allocator1>& Y, 00841 string function, string op) 00842 { 00843 if (X.GetLength() != Y.GetM()) 00844 throw WrongDim(function, string("Operation ") + op 00845 + string(" not permitted:") 00846 + string("\n X (") + to_str(&X) + string(") is a ") 00847 + string("vector of length ") + to_str(X.GetLength()) 00848 + string(";\n Y (") + to_str(&Y) + string(") is a ") 00849 + string("vector of length ") + to_str(Y.GetM()) 00850 + string(".")); 00851 } 00852 00853 00855 00865 template <class T0, template <class U0> class Allocator0, 00866 class T1, template <class U1> class Allocator1> 00867 void 00868 CheckDim(const 00869 Vector<FloatDouble, DenseSparseCollection, Allocator0<T0> >& X, 00870 const 00871 Vector<FloatDouble, DenseSparseCollection, Allocator1<T1> >& Y, 00872 string function, string op) 00873 { 00874 if (X.GetNvector() != Y.GetNvector()) 00875 throw WrongDim(function, string("Operation ") + op 00876 + string(" not permitted:") 00877 + string("\n X (") + to_str(&X) + string(") is a ") 00878 + string("vector of length ") + to_str(X.GetNvector()) 00879 + string(";\n Y (") + to_str(&Y) + string(") is a ") 00880 + string("vector of length ") + to_str(Y.GetNvector()) 00881 + string(".")); 00882 } 00883 00884 00885 // CHECKDIM // 00887 00888 00890 // CONJUGATE // 00891 00892 00894 template<class T, class Prop, class Allocator> 00895 void Conjugate(Vector<T, Prop, Allocator>& X) 00896 { 00897 for (int i = 0; i < X.GetM(); i++) 00898 X(i) = conj(X(i)); 00899 } 00900 00901 00903 template<class T, class Allocator> 00904 void Conjugate(Vector<T, VectSparse, Allocator>& X) 00905 { 00906 for (int i = 0; i < X.GetSize(); i++) 00907 X.Value(i) = conj(X.Value(i)); 00908 } 00909 00910 00911 // CONJUGATE // 00913 00914 00915 } // namespace Seldon. 00916 00917 00918 #endif