TheAlgorithms/C++ 1.0.0
All the algorithms implemented in C++
Loading...
Searching...
No Matches
gram_schmidt.cpp
Go to the documentation of this file.
1
31#include <array>
32#include <cassert>
33#include <cmath>
34#include <iostream>
35
36#include "math.h"
37
42namespace numerical_methods {
48namespace gram_schmidt {
59double dot_product(const std::array<double, 10>& x,
60 const std::array<double, 10>& y, const int& c) {
61 double sum = 0;
62 for (int i = 0; i < c; ++i) {
63 sum += x[i] * y[i];
64 }
65 return sum;
66}
67
79double projection(const std::array<double, 10>& x,
80 const std::array<double, 10>& y, const int& c) {
81 double dot =
82 dot_product(x, y, c);
83 double anorm =
84 dot_product(y, y, c);
85 double factor =
86 dot /
87 anorm;
89 return factor;
90}
91
101void display(const int& r, const int& c,
102 const std::array<std::array<double, 10>, 20>& B) {
103 for (int i = 0; i < r; ++i) {
104 std::cout << "Vector " << i + 1 << ": ";
105 for (int j = 0; j < c; ++j) {
106 std::cout << B[i][j] << " ";
107 }
108 std::cout << '\n';
109 }
110}
111
121void gram_schmidt(int r, const int& c,
122 const std::array<std::array<double, 10>, 20>& A,
123 std::array<std::array<double, 10>, 20> B) {
124 if (c < r) {
125 std::cout << "Dimension of vector is less than number of vector, hence "
126 "\n first "
127 << c << " vectors are orthogonalised\n";
128 r = c;
129 }
130
131 int k = 1;
132
133 while (k <= r) {
134 if (k == 1) {
135 for (int j = 0; j < c; j++)
136 B[0][j] = A[0][j];
137 }
138
139 else {
140 std::array<double, 10>
141 all_projection{};
142 for (int i = 0; i < c; ++i) {
143 all_projection[i] = 0;
144 }
145
146 int l = 1;
147 while (l < k) {
148 std::array<double, 10>
149 temp{};
150 double factor = NAN;
152 factor = projection(A[k - 1], B[l - 1], c);
153 for (int i = 0; i < c; ++i) {
154 temp[i] = B[l - 1][i] * factor;
155 }
156 for (int j = 0; j < c; ++j) {
157 all_projection[j] =
158 all_projection[j] +
159 temp[j];
161 }
162 l++;
163 }
164 for (int i = 0; i < c; ++i) {
165 B[k - 1][i] =
166 A[k - 1][i] -
167 all_projection[i];
169 }
170 }
171 k++;
172 }
173 display(r, c, B); // for displaying orthogoanlised vectors
174}
175} // namespace gram_schmidt
176} // namespace numerical_methods
181static void test() {
182 std::array<std::array<double, 10>, 20> a1 = {
183 {{1, 0, 1, 0}, {1, 1, 1, 1}, {0, 1, 2, 1}}};
184 std::array<std::array<double, 10>, 20> b1 = {{0}};
185 double dot1 = 0;
186 numerical_methods::gram_schmidt::gram_schmidt(3, 4, a1, b1);
187 int flag = 1;
188 for (int i = 0; i < 2; ++i) {
189 for (int j = i + 1; j < 3; ++j) {
190 dot1 = fabs(
191 numerical_methods::gram_schmidt::dot_product(b1[i], b1[j], 4));
192 if (dot1 > 0.1) {
193 flag = 0;
194 break;
195 }
196 }
197 }
198 if (flag == 0)
199 std::cout << "Vectors are linearly dependent\n";
200 assert(flag == 1);
201 std::cout << "Passed Test Case 1\n ";
202
203 std::array<std::array<double, 10>, 20> a2 = {{{3, 1}, {2, 2}}};
204 std::array<std::array<double, 10>, 20> b2 = {{0}};
205 double dot2 = 0;
206 numerical_methods::gram_schmidt::gram_schmidt(2, 2, a2, b2);
207 flag = 1;
208 for (int i = 0; i < 1; ++i) {
209 for (int j = i + 1; j < 2; ++j) {
210 dot2 = fabs(
211 numerical_methods::gram_schmidt::dot_product(b2[i], b2[j], 2));
212 if (dot2 > 0.1) {
213 flag = 0;
214 break;
215 }
216 }
217 }
218 if (flag == 0)
219 std::cout << "Vectors are linearly dependent\n";
220 assert(flag == 1);
221 std::cout << "Passed Test Case 2\n";
222
223 std::array<std::array<double, 10>, 20> a3 = {{{1, 2, 2}, {-4, 3, 2}}};
224 std::array<std::array<double, 10>, 20> b3 = {{0}};
225 double dot3 = 0;
226 numerical_methods::gram_schmidt::gram_schmidt(2, 3, a3, b3);
227 flag = 1;
228 for (int i = 0; i < 1; ++i) {
229 for (int j = i + 1; j < 2; ++j) {
230 dot3 = fabs(
231 numerical_methods::gram_schmidt::dot_product(b3[i], b3[j], 3));
232 if (dot3 > 0.1) {
233 flag = 0;
234 break;
235 }
236 }
237 }
238 if (flag == 0)
239 std::cout << "Vectors are linearly dependent\n";
240 assert(flag == 1);
241 std::cout << "Passed Test Case 3\n";
242}
243
248int main() {
249 int r = 0, c = 0;
250 test(); // perform self tests
251 std::cout << "Enter the dimension of your vectors\n";
252 std::cin >> c;
253 std::cout << "Enter the number of vectors you will enter\n";
254 std::cin >> r;
255
256 std::array<std::array<double, 10>, 20>
257 A{};
258 std::array<std::array<double, 10>, 20> B = {
259 {0}};
261 for (int i = 0; i < r; ++i) {
262 std::cout << "Enter vector " << i + 1
263 << '\n';
264 for (int j = 0; j < c; ++j) {
265 std::cout << "Value " << j + 1 << "th of vector: ";
266 std::cin >> A[i][j];
267 }
268 std::cout << '\n';
269 }
270
271 numerical_methods::gram_schmidt::gram_schmidt(r, c, A, B);
272
273 double dot = 0;
274 int flag = 1;
275 for (int i = 0; i < r - 1; ++i) {
276 for (int j = i + 1; j < r; ++j) {
277 dot = fabs(
278 numerical_methods::gram_schmidt::dot_product(B[i], B[j], c));
279 if (dot > 0.1)
281 {
282 flag = 0;
283 break;
284 }
285 }
286 }
287 if (flag == 0)
288 std::cout << "Vectors are linearly dependent\n";
289 return 0;
290}
double projection(const std::array< double, 10 > &x, const std::array< double, 10 > &y, const int &c)
static void test()
double dot_product(const std::array< double, 10 > &x, const std::array< double, 10 > &y, const int &c)
int main()
Main Function.
Functions for Gram Schmidt Orthogonalisation Process