00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #ifndef SELDON_FILE_ITERATIVE_BICGSTAB_CXX
00022
00023 namespace Seldon
00024 {
00025
00027
00043 template <class Titer, class Matrix1, class Vector1, class Preconditioner>
00044 int BiCgStab(Matrix1& A, Vector1& x, const Vector1& b,
00045 Preconditioner& M, Iteration<Titer> & iter)
00046 {
00047 const int N = A.GetM();
00048 if (N <= 0)
00049 return 0;
00050
00051 typedef typename Vector1::value_type Complexe;
00052 Complexe rho_1, rho_2(0), alpha(0), beta, omega(0), sigma;
00053 Vector1 p(b), phat(b), s(b), shat(b), t(b), v(b), r(b), rtilde(b);
00054
00055
00056 int success_init = iter.Init(b);
00057 if (success_init != 0)
00058 return iter.ErrorCode();
00059
00060
00061 Copy(b, r);
00062 if (!iter.IsInitGuess_Null())
00063 MltAdd(Complexe(-1), A, x, Complexe(1), r);
00064 else
00065 x.Zero();
00066
00067 Copy(r, rtilde);
00068
00069 iter.SetNumberIteration(0);
00070
00071 while (! iter.Finished(r))
00072 {
00073
00074 rho_1 = DotProdConj(rtilde, r);
00075 if (rho_1 == Complexe(0))
00076 {
00077 iter.Fail(1, "Bicgstab breakdown #1");
00078 break;
00079 }
00080
00081 if (iter.First())
00082 Copy(r, p);
00083 else
00084 {
00085 if (omega == Complexe(0))
00086 {
00087 iter.Fail(2, "Bicgstab breakdown #2");
00088 break;
00089 }
00090
00091
00092 beta = (rho_1 / rho_2) * (alpha / omega);
00093 Add(-omega, v, p);
00094 Mlt(beta, p);
00095 Add(Complexe(1), r, p);
00096 }
00097
00098 M.Solve(A, p, phat);
00099
00100
00101 Mlt(A, phat, v);
00102
00103
00104 sigma = DotProdConj(rtilde, v);
00105 if (sigma == Complexe(0))
00106 {
00107 iter.Fail(3, "Bicgstab breakdown #3");
00108 break;
00109 }
00110 alpha = rho_1 / sigma;
00111 Copy(r, s);
00112 Add(-alpha, v, s);
00113
00114
00115 ++iter;
00116 if (iter.Finished(s))
00117 {
00118
00119 Add(alpha, phat, x);
00120 break;
00121 }
00122
00123
00124 M.Solve(A, s, shat);
00125
00126
00127 Mlt(A, shat, t);
00128
00129 omega = DotProdConj(t, s) / DotProdConj(t, t);
00130
00131
00132 Add(alpha, phat, x);
00133 Add(omega, shat, x);
00134
00135
00136 Copy(s, r);
00137 Add(-omega, t, r);
00138
00139 rho_2 = rho_1;
00140
00141 ++iter;
00142 }
00143
00144 return iter.ErrorCode();
00145 }
00146
00147 }
00148
00149 #define SELDON_FILE_ITERATIVE_BICGSTAB_CXX
00150 #endif