Repository navigation
Expand file tree
/
Copy pathVector.cpp
More file actions
179 lines (155 loc) · 4.26 KB
/
Copy pathVector.cpp
File metadata and controls
179 lines (155 loc) · 4.26 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
#include "Vector.h"
#include "Matrix.h"
#define EPSILON 1e-10
// check the move constructors. Whether or not to add move
Vector::Vector(const Matrix &m){
vec.reserve(m.order().first * m.order().second);
for(int i{0}; i<m.order().second; i++){
vec.insert(std::end(vec), std::begin(m.at(i).vec), std::end(m.at(i).vec));
}
}
// Arithmetic operations
Vector Vector::operator + (const Vector &v) const
{
if (size()!=v.size())
{
std::cerr<<"Invalid addition"<<std::endl;
throw std::invalid_argument("Vectors incompatible for addition.");
}
Vector sum(size());
for(int i{0};i<size();i++)
{
sum.at(i) = at(i)+v.at(i);
}
return sum;
}
Vector Vector::operator - (const Vector &v) const
{
if (size()!=v.size())
{
std::cerr<<"Invalid subtraction"<<std::endl;
throw std::invalid_argument("Vectors incompatible for subtraction.");
}
Vector diff(size());
for(int i{0};i<size();i++)
{
diff.at(i) = at(i)-v.at(i);
}
return diff;
}
Vector Vector::operator * (const double &d) const
{
Vector v(size());
for (int i{0};i<size();i++)
v.at(i) = d * at(i);
return v;
}
Vector Vector::operator / (double d) const
{
if (std::abs(d) < EPSILON)
{
std::cerr<<"Division by 0"<<std::endl;
throw std::invalid_argument("Cannot divide by 0");
}
return (*this)*(1/d);
}
const Vector &Vector::operator+=(const Vector &v){
if (size()!=v.size())
{
std::cerr<<"Invalid addition"<<std::endl;
throw 0;
}
for (int i = 0; i < size(); i++)
at(i) = at(i) + v.at(i);
return *this;
}
const Vector &Vector::operator-=(const Vector &v){
if (size()!=v.size())
{
std::cerr<<"Invalid subtraction"<<std::endl;
throw 0;
}
for (int i = 0; i < size(); i++)
at(i) = at(i) - v.at(i);
return *this;
}
const Vector &Vector::operator*=(const double &factor){
for (auto &elem: vec)
elem = elem * factor;
return *this;
}
const Vector &Vector::operator/=(double factor){
if (std::abs(factor)<EPSILON)
{
std::cerr<<"Division by 0"<<std::endl;
throw 0;
}
for (int i = 0; i < size(); i++)
at(i) = at(i) / factor;
return *this;
}
// inner products and norm
double Vector::dot(const Vector &v) const
{
if (this->size()!=v.size())
{
std::cerr<<"Invalid dot product"<<std::endl;
throw std::invalid_argument("Vectors do not have the same dimension. Cannot take dot product.");
}
double pdt{0};
for(int i{0};i<v.size();i++)
pdt += at(i) * v.at(i);
return pdt;
}
double Vector::norm(int k) const{
double res = 0;
for (int i = 0; i < size(); i++)
res += std::pow(at(i), k);
return pow(res, 1.0/k);
}
Vector Vector::normalized(bool modify, int k){
Vector res(size());
double norm_ = norm(k);
if (std::abs(norm_) < EPSILON)
throw "Cannot normalize zero vector";
for (int i = 0; i < size(); i++)
res[i] = at(i)/norm_;
if (modify)
*this = res;
return res;
}
// special function, required for reduced matrix forms
Vector Vector::set_component_to_1(int index, bool modify){
if (std::abs(at(index)) < EPSILON){
std::cerr << "Element is 0 - cannot scale to 1\n";
throw std::invalid_argument("Element is 0 - cannot scale to 1\n");
}
Vector res(size());
for (int i = 0; i < size(); i++)
res[i] = at(i)/at(index);
if (modify)
*this = res;
return res;
}
// ===================== Global functions ============================= //
Vector operator*(const double &factor, const Vector &v){
return v * factor;
}
std::ostream& operator<<(std::ostream &ost, const Vector &v){
if (v.size() == 0){
ost << "[]";
return ost;
}
ost << '[';
for(auto it = v.begin(); it != v.end(); it++)
{
if(std::abs(*it)<EPSILON)
ost<<0;
else
ost << *it;
if(it + 1 != v.end())
ost << ", ";
}
std::cout<<"]";
return ost;
}