-
Notifications
You must be signed in to change notification settings - Fork 1.6k
/
Copy pathVectorExtensions.cs
152 lines (131 loc) · 4.31 KB
/
VectorExtensions.cs
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
using System;
namespace Utilities.Extensions;
public static class VectorExtensions
{
/// <summary>
/// Makes a copy of a vector. Changes to the copy should not affect the original.
/// </summary>
/// <param name="vector">The vector.</param>
/// <returns>The copy.</returns>
public static double[] Copy(this double[] vector)
{
var result = new double[vector.Length];
for (var i = 0; i < vector.Length; i++)
{
result[i] = vector[i];
}
return result;
}
/// <summary>
/// Computes the outer product of two vectors.
/// </summary>
/// <param name="lhs">The LHS vector.</param>
/// <param name="rhs">The RHS vector.</param>
/// <returns>The outer product of the two vector.</returns>
public static double[,] OuterProduct(this double[] lhs, double[] rhs)
{
var result = new double[lhs.Length, rhs.Length];
for (var i = 0; i < lhs.Length; i++)
{
for (var j = 0; j < rhs.Length; j++)
{
result[i, j] = lhs[i] * rhs[j];
}
}
return result;
}
/// <summary>
/// Computes the dot product of two vectors.
/// </summary>
/// <param name="lhs">The LHS vector.</param>
/// <param name="rhs">The RHS vector.</param>
/// <returns>The dot product of the two vector.</returns>
/// <exception cref="ArgumentException">Dimensions of vectors do not match.</exception>
public static double Dot(this double[] lhs, double[] rhs)
{
if (lhs.Length != rhs.Length)
{
throw new ArgumentException("Dot product arguments must have same dimension");
}
double result = 0;
for (var i = 0; i < lhs.Length; i++)
{
result += lhs[i] * rhs[i];
}
return result;
}
/// <summary>
/// Computes the magnitude of a vector.
/// </summary>
/// <param name="vector">The vector.</param>
/// <returns>The magnitude.</returns>
public static double Magnitude(this double[] vector)
{
var magnitude = Dot(vector, vector);
magnitude = Math.Sqrt(magnitude);
return magnitude;
}
/// <summary>
/// Returns the scaled vector.
/// </summary>
/// <param name="vector">The vector.</param>
/// <param name="factor">Scale factor.</param>
/// <returns>The unit vector.</returns>
public static double[] Scale(this double[] vector, double factor)
{
var result = new double[vector.Length];
for (var i = 0; i < vector.Length; i++)
{
result[i] = vector[i] * factor;
}
return result;
}
/// <summary>
/// Transpose 1d row vector to column vector.
/// </summary>
/// <param name="source">Input 1d vector.</param>
/// <returns>Column vector.</returns>
public static double[,] ToColumnVector(this double[] source)
{
var columnVector = new double[source.Length, 1];
for (var i = 0; i < source.Length; i++)
{
columnVector[i, 0] = source[i];
}
return columnVector;
}
/// <summary>
/// Transpose column vector to 1d row vector.
/// </summary>
/// <param name="source">Input column vector.</param>
/// <returns>Row vector.</returns>
/// <exception cref="InvalidOperationException">The column vector should have only 1 element in width.</exception>
public static double[] ToRowVector(this double[,] source)
{
if (source.GetLength(1) != 1)
{
throw new InvalidOperationException("The column vector should have only 1 element in width.");
}
var rowVector = new double[source.Length];
for (var i = 0; i < rowVector.Length; i++)
{
rowVector[i] = source[i, 0];
}
return rowVector;
}
/// <summary>
/// Generates a diagonal matrix from an specified vector.
/// </summary>
/// <param name="vector">The input vector.</param>
/// <returns>A Diagonal matrix.</returns>
public static double[,] ToDiagonalMatrix(this double[] vector)
{
var len = vector.Length;
var result = new double[len, len];
for (var i = 0; i < len; i++)
{
result[i, i] = vector[i];
}
return result;
}
}