From 5ff5cc7be8eabb7b36a5eb8b2ccbbc63a9411f24 Mon Sep 17 00:00:00 2001 From: That-One-Nerd Date: Fri, 14 Jul 2023 21:08:50 -0400 Subject: [PATCH] Some changes to the matrix types have been made. --- Changelog.md | 40 ++++++++++++++++- Nerd_STF/Mathematics/Abstract/IMatrix.cs | 20 +++++++-- Nerd_STF/Mathematics/Algebra/Matrix.cs | 14 ++++++ Nerd_STF/Mathematics/Algebra/Matrix2x2.cs | 37 +++++++++++++++- Nerd_STF/Mathematics/Algebra/Matrix3x3.cs | 42 ++++++++++++++++++ Nerd_STF/Mathematics/Algebra/Matrix4x4.cs | 52 ++++++++++++++++++++++- 6 files changed, 197 insertions(+), 8 deletions(-) diff --git a/Changelog.md b/Changelog.md index ee2d21a..1e72ab1 100644 --- a/Changelog.md +++ b/Changelog.md @@ -2,7 +2,7 @@ TODO -added row operations, fixed cofactor bugs, added setters +added row operations, fixed cofactor bugs, added setters and more stuff to imatrix Here's the full changelog: ``` @@ -11,29 +11,65 @@ Here's the full changelog: * Abstract * IMatrix + AddRow(int, int, float) + + AddRowMutable(int, int, float) + Cofactor() + + GetColumn(int) + + GetRow(int) + ScaleRow(int, float) + + ScaleRowMutable(int, float) + + SetColumn(int, float[]) + + SetRow(int, float[]) + + Size + SwapRows(int, int) - + SolveRowEchelon() + + SwapRowsMutable(int, int) + + this[int, int] + + this[Index, Index] * Algebra * Matrix + AddRow(int, int, float) + + AddRowMutable(int, int, float) + ScaleRow(int, float) + + ScaleRowMutable(int, float) + SwapRows(int, int) + + SwapRowsMutable(int, int) = Fixed a blunder in `SignGrid(Int2)` with signs being incorrectly placed on matrixes with even column count. * Matrix2x2 + AddRow(int, int, float) + + AddRowMutable(int, int, float) + + GetColumn(int) + + GetRow(int) + ScaleRow(int, float) + + ScaleRowMutable(int, float) + + SetColumn(int, float[]) + + SetRow(int, float[]) + + Size + SwapRows(int, int) + + SwapRowsMutable(int, int) = Fixed a blunder in `Cofactor()` with the position of elements. * Matrix3x3 + AddRow(int, int, float) + + AddRowMutable(int, int, float) + + GetColumn(int) + + GetRow(int) + ScaleRow(int, float) + + ScaleRowMutable(int, float) + + SetColumn(int, float[]) + + SetRow(int, float[]) + + Size + SwapRows(int, int) + + SwapRowsMutable(int, int) * Matrix4x4 + AddRow(int, int, float) + + AddRowMutable(int, int, float) + + GetColumn(int) + + GetRow(int) + ScaleRow(int, float) + + ScaleRowMutable(int, float) + + SetColumn(int, float[]) + + SetRow(int, float[]) + + Size + SwapRows(int, int) + + SwapRowsMutable(int, int) * NumberSystems * Complex + operator Complex(SystemComplex) diff --git a/Nerd_STF/Mathematics/Abstract/IMatrix.cs b/Nerd_STF/Mathematics/Abstract/IMatrix.cs index cbcc7bf..f664310 100644 --- a/Nerd_STF/Mathematics/Abstract/IMatrix.cs +++ b/Nerd_STF/Mathematics/Abstract/IMatrix.cs @@ -5,17 +5,29 @@ public interface IMatrix : IAbsolute, ICeiling, IClamp, IDivide, ISubtract, ISum where T : IMatrix { + public Int2 Size { get; } + + public float this[int r, int c] { get; set; } + public float this[Index r, Index c] { get; set; } + public T Adjugate(); public T Cofactor(); public float Determinant(); public T? Inverse(); public T Transpose(); - public T AddRow(int rowToChange, int referenceRow, float factor = 1); - public T ScaleRow(int rowIndex, float value); - public T SwapRows(int rowA, int rowB); + public float[] GetColumn(int column); + public float[] GetRow(int row); - //public T SolveRowEchelon(); + public void SetColumn(int column, float[] value); + public void SetRow(int row, float[] values); + + public T AddRow(int rowToChange, int referenceRow, float factor = 1); + public void AddRowMutable(int rowToChange, int referenceRow, float factor = 1); + public T ScaleRow(int rowIndex, float value); + public void ScaleRowMutable(int rowIndex, float value); + public T SwapRows(int rowA, int rowB); + public void SwapRowsMutable(int rowA, int rowB); } public interface IMatrix : IMatrix where This : IMatrix diff --git a/Nerd_STF/Mathematics/Algebra/Matrix.cs b/Nerd_STF/Mathematics/Algebra/Matrix.cs index 09ea5c5..8ea5e0f 100644 --- a/Nerd_STF/Mathematics/Algebra/Matrix.cs +++ b/Nerd_STF/Mathematics/Algebra/Matrix.cs @@ -285,6 +285,10 @@ public class Matrix : IMatrix else return @this[r, c]; }); } + public void AddRowMutable(int rowToChange, int referenceRow, float factor) + { + for (int c = 0; c < Size.y; c++) this[rowToChange, c] += this[referenceRow, c] * factor; + } public Matrix ScaleRow(int rowIndex, float factor) { Matrix @this = this; @@ -294,6 +298,10 @@ public class Matrix : IMatrix else return @this[r, c]; }); } + public void ScaleRowMutable(int rowIndex, float factor) + { + for (int c = 0; c < Size.y; c++) this[rowIndex, c] *= factor; + } public Matrix SwapRows(int rowA, int rowB) { Matrix @this = this; @@ -304,6 +312,12 @@ public class Matrix : IMatrix else return @this[r, c]; }); } + public void SwapRowsMutable(int rowA, int rowB) + { + float[] dataA = GetRow(rowA), dataB = GetRow(rowB); + SetRow(rowA, dataB); + SetRow(rowB, dataA); + } public override bool Equals([NotNullWhen(true)] object? obj) { diff --git a/Nerd_STF/Mathematics/Algebra/Matrix2x2.cs b/Nerd_STF/Mathematics/Algebra/Matrix2x2.cs index 0eb26aa..165ecf3 100644 --- a/Nerd_STF/Mathematics/Algebra/Matrix2x2.cs +++ b/Nerd_STF/Mathematics/Algebra/Matrix2x2.cs @@ -52,6 +52,8 @@ public record class Matrix2x2 : IStaticMatrix } } + public Int2 Size => (2, 2); + public float r1c1, r2c1, r1c2, r2c2; public Matrix2x2(float all) : this(all, all, all, all) { } @@ -241,6 +243,24 @@ public record class Matrix2x2 : IStaticMatrix { r1c2, r2c2 } }); + public float[] GetColumn(int column) => new[] { this[0, column], this[1, column] }; + public float[] GetRow(int row) => new[] { this[row, 0], this[row, 1] }; + + public void SetColumn(int column, float[] vals) + { + if (vals.Length < 2) + throw new InvalidSizeException("Array must contain enough values to fill the column."); + this[0, column] = vals[0]; + this[1, column] = vals[1]; + } + public void SetRow(int row, float[] vals) + { + if (vals.Length < 2) + throw new InvalidSizeException("Array must contain enough values to fill the row."); + this[row, 0] = vals[0]; + this[row, 1] = vals[1]; + } + public Matrix2x2 AddRow(int rowToChange, int referenceRow, float factor = 1) { Matrix2x2 @this = this; @@ -250,6 +270,11 @@ public record class Matrix2x2 : IStaticMatrix else return @this[r, c]; }); } + public void AddRowMutable(int rowToChange, int referenceRow, float factor) + { + this[rowToChange, 0] += this[referenceRow, 0] * factor; + this[rowToChange, 1] += this[referenceRow, 1] * factor; + } public Matrix2x2 ScaleRow(int rowIndex, float factor) { Matrix2x2 @this = this; @@ -259,6 +284,11 @@ public record class Matrix2x2 : IStaticMatrix else return @this[r, c]; }); } + public void ScaleRowMutable(int rowIndex, float factor) + { + this[rowIndex, 0] *= factor; + this[rowIndex, 1] *= factor; + } public Matrix2x2 SwapRows(int rowA, int rowB) { Matrix2x2 @this = this; @@ -269,7 +299,12 @@ public record class Matrix2x2 : IStaticMatrix else return @this[r, c]; }); } - + public void SwapRowsMutable(int rowA, int rowB) + { + float[] dataA = GetRow(rowA), dataB = GetRow(rowB); + SetRow(rowA, dataB); + SetRow(rowB, dataA); + } public virtual bool Equals(Matrix2x2? other) { diff --git a/Nerd_STF/Mathematics/Algebra/Matrix3x3.cs b/Nerd_STF/Mathematics/Algebra/Matrix3x3.cs index 8a8d66d..79c4ebb 100644 --- a/Nerd_STF/Mathematics/Algebra/Matrix3x3.cs +++ b/Nerd_STF/Mathematics/Algebra/Matrix3x3.cs @@ -78,6 +78,8 @@ public record class Matrix3x3 : IStaticMatrix } } + public Int2 Size => (3, 3); + public float r1c1, r2c1, r3c1, r1c2, r2c2, r3c2, r1c3, r2c3, r3c3; public Matrix3x3(float all) : this(all, all, all, all, all, all, all, all, all) { } @@ -336,6 +338,28 @@ public record class Matrix3x3 : IStaticMatrix { r1c3, r2c3, r3c3 } }); + public float[] GetColumn(int column) => new[] { this[0, column], this[1, column], this[2, column] }; + public float[] GetRow(int row) => new[] { this[row, 0], this[row, 1], this[row, 2] }; + + public void SetColumn(int column, float[] vals) + { + if (vals.Length < 3) + throw new InvalidSizeException("Array must contain enough values to fill the column."); + + this[0, column] = vals[0]; + this[1, column] = vals[1]; + this[2, column] = vals[2]; + } + public void SetRow(int row, float[] vals) + { + if (vals.Length < 3) + throw new InvalidSizeException("Array must contain enough values to fill the row."); + + this[row, 0] = vals[0]; + this[row, 1] = vals[1]; + this[row, 2] = vals[2]; + } + public Matrix3x3 AddRow(int rowToChange, int referenceRow, float factor = 1) { Matrix3x3 @this = this; @@ -345,6 +369,12 @@ public record class Matrix3x3 : IStaticMatrix else return @this[r, c]; }); } + public void AddRowMutable(int rowToChange, int referenceRow, float factor) + { + this[rowToChange, 0] += this[referenceRow, 0] * factor; + this[rowToChange, 1] += this[referenceRow, 1] * factor; + this[rowToChange, 2] += this[referenceRow, 2] * factor; + } public Matrix3x3 ScaleRow(int rowIndex, float factor) { Matrix3x3 @this = this; @@ -354,6 +384,12 @@ public record class Matrix3x3 : IStaticMatrix else return @this[r, c]; }); } + public void ScaleRowMutable(int rowIndex, float factor) + { + this[rowIndex, 0] *= factor; + this[rowIndex, 1] *= factor; + this[rowIndex, 2] *= factor; + } public Matrix3x3 SwapRows(int rowA, int rowB) { Matrix3x3 @this = this; @@ -364,6 +400,12 @@ public record class Matrix3x3 : IStaticMatrix else return @this[r, c]; }); } + public void SwapRowsMutable(int rowA, int rowB) + { + float[] dataA = GetRow(rowA), dataB = GetRow(rowB); + SetRow(rowA, dataB); + SetRow(rowB, dataA); + } public virtual bool Equals(Matrix3x3? other) { diff --git a/Nerd_STF/Mathematics/Algebra/Matrix4x4.cs b/Nerd_STF/Mathematics/Algebra/Matrix4x4.cs index 262da21..dc35b12 100644 --- a/Nerd_STF/Mathematics/Algebra/Matrix4x4.cs +++ b/Nerd_STF/Mathematics/Algebra/Matrix4x4.cs @@ -1,4 +1,6 @@ -namespace Nerd_STF.Mathematics.Algebra; +using System.Data.Common; + +namespace Nerd_STF.Mathematics.Algebra; public record class Matrix4x4 : IStaticMatrix { @@ -108,6 +110,8 @@ public record class Matrix4x4 : IStaticMatrix } } + public Int2 Size => (4, 4); + public float r1c1, r2c1, r3c1, r4c1, r1c2, r2c2, r3c2, r4c2, r1c3, r2c3, r3c3, r4c3, r1c4, r2c4, r3c4, r4c4; public Matrix4x4(float all) : this(all, all, all, all, all, @@ -451,6 +455,32 @@ public record class Matrix4x4 : IStaticMatrix { r1c4, r2c4, r3c4, r4c4 } }); + public float[] GetColumn(int column) => + new[] { this[0, column], this[1, column], this[2, column], this[3, column] }; + public float[] GetRow(int row) => + new[] { this[row, 0], this[row, 1], this[row, 2], this[row, 3] }; + + public void SetColumn(int column, float[] vals) + { + if (vals.Length < 4) + throw new InvalidSizeException("Array must contain enough values to fill the column."); + + this[0, column] = vals[0]; + this[1, column] = vals[1]; + this[2, column] = vals[2]; + this[3, column] = vals[3]; + } + public void SetRow(int row, float[] vals) + { + if (vals.Length < 4) + throw new InvalidSizeException("Array must contain enough values to fill the row."); + + this[row, 0] = vals[0]; + this[row, 1] = vals[1]; + this[row, 2] = vals[2]; + this[row, 3] = vals[3]; + } + public Matrix4x4 AddRow(int rowToChange, int referenceRow, float factor = 1) { Matrix4x4 @this = this; @@ -460,6 +490,13 @@ public record class Matrix4x4 : IStaticMatrix else return @this[r, c]; }); } + public void AddRowMutable(int rowToChange, int referenceRow, float factor) + { + this[rowToChange, 0] += this[referenceRow, 0] * factor; + this[rowToChange, 1] += this[referenceRow, 1] * factor; + this[rowToChange, 2] += this[referenceRow, 2] * factor; + this[rowToChange, 3] += this[referenceRow, 3] * factor; + } public Matrix4x4 ScaleRow(int rowIndex, float factor) { Matrix4x4 @this = this; @@ -469,6 +506,13 @@ public record class Matrix4x4 : IStaticMatrix else return @this[r, c]; }); } + public void ScaleRowMutable(int rowIndex, float factor) + { + this[rowIndex, 0] *= factor; + this[rowIndex, 1] *= factor; + this[rowIndex, 2] *= factor; + this[rowIndex, 3] *= factor; + } public Matrix4x4 SwapRows(int rowA, int rowB) { Matrix4x4 @this = this; @@ -479,6 +523,12 @@ public record class Matrix4x4 : IStaticMatrix else return @this[r, c]; }); } + public void SwapRowsMutable(int rowA, int rowB) + { + float[] dataA = GetRow(rowA), dataB = GetRow(rowB); + SetRow(rowA, dataB); + SetRow(rowB, dataA); + } public virtual bool Equals(Matrix4x4? other) {