From c51d84d79d189b752430e53b10fd56e2c52d09b4 Mon Sep 17 00:00:00 2001 From: James Jackson-South Date: Wed, 16 Oct 2024 21:25:07 +1000 Subject: [PATCH] Use double precision for accuracy --- .../Helpers/GaussianEliminationSolver.cs | 12 +++++----- .../Common/Helpers/QuadDistortionHelper.cs | 10 ++++---- .../Common/GaussianEliminationSolverTest.cs | 24 +++++++++---------- 3 files changed, 23 insertions(+), 23 deletions(-) diff --git a/src/ImageSharp/Common/Helpers/GaussianEliminationSolver.cs b/src/ImageSharp/Common/Helpers/GaussianEliminationSolver.cs index fdb4790609..ee87cdc864 100644 --- a/src/ImageSharp/Common/Helpers/GaussianEliminationSolver.cs +++ b/src/ImageSharp/Common/Helpers/GaussianEliminationSolver.cs @@ -20,24 +20,24 @@ internal static class GaussianEliminationSolver /// The matrix passed to this method must be a square matrix. /// If the matrix is singular (i.e., has no unique solution), an will be thrown. /// - public static void Solve(float[][] matrix, float[] result) + public static void Solve(double[][] matrix, double[] result) { TransformToRowEchelonForm(matrix, result); ApplyBackSubstitution(matrix, result); } - private static void TransformToRowEchelonForm(float[][] matrix, float[] result) + private static void TransformToRowEchelonForm(double[][] matrix, double[] result) { int colCount = matrix.Length; int rowCount = matrix[0].Length; int pivotRow = 0; for (int pivotCol = 0; pivotCol < colCount; pivotCol++) { - float maxValue = float.Abs(matrix[pivotRow][pivotCol]); + double maxValue = double.Abs(matrix[pivotRow][pivotCol]); int maxIndex = pivotRow; for (int r = pivotRow + 1; r < rowCount; r++) { - float value = float.Abs(matrix[r][pivotCol]); + double value = double.Abs(matrix[r][pivotCol]); if (value > maxValue) { maxIndex = r; @@ -55,7 +55,7 @@ internal static class GaussianEliminationSolver for (int r = pivotRow + 1; r < rowCount; r++) { - float fraction = matrix[r][pivotCol] / matrix[pivotRow][pivotCol]; + double fraction = matrix[r][pivotCol] / matrix[pivotRow][pivotCol]; for (int c = pivotCol + 1; c < colCount; c++) { matrix[r][c] -= matrix[pivotRow][c] * fraction; @@ -69,7 +69,7 @@ internal static class GaussianEliminationSolver } } - private static void ApplyBackSubstitution(float[][] matrix, float[] result) + private static void ApplyBackSubstitution(double[][] matrix, double[] result) { int rowCount = matrix[0].Length; diff --git a/src/ImageSharp/Common/Helpers/QuadDistortionHelper.cs b/src/ImageSharp/Common/Helpers/QuadDistortionHelper.cs index dcd89bafb2..c1eee3daff 100644 --- a/src/ImageSharp/Common/Helpers/QuadDistortionHelper.cs +++ b/src/ImageSharp/Common/Helpers/QuadDistortionHelper.cs @@ -40,7 +40,7 @@ internal static class QuadDistortionHelper PointF q3 = bottomRight; PointF q4 = bottomLeft; - float[][] matrixData = + double[][] matrixData = [ [p1.X, p1.Y, 1, 0, 0, 0, -p1.X * q1.X, -p1.Y * q1.X], [0, 0, 0, p1.X, p1.Y, 1, -p1.X * q1.Y, -p1.Y * q1.Y], @@ -52,7 +52,7 @@ internal static class QuadDistortionHelper [0, 0, 0, p4.X, p4.Y, 1, -p4.X * q4.Y, -p4.Y * q4.Y], ]; - float[] b = + double[] b = [ q1.X, q1.Y, @@ -68,10 +68,10 @@ internal static class QuadDistortionHelper #pragma warning disable SA1117 Matrix4x4 projectionMatrix = new( - b[0], b[3], 0, b[6], - b[1], b[4], 0, b[7], + (float)b[0], (float)b[3], 0, (float)b[6], + (float)b[1], (float)b[4], 0, (float)b[7], 0, 0, 1, 0, - b[2], b[5], 0, 1); + (float)b[2], (float)b[5], 0, 1); #pragma warning restore SA1117 return projectionMatrix; diff --git a/tests/ImageSharp.Tests/Common/GaussianEliminationSolverTest.cs b/tests/ImageSharp.Tests/Common/GaussianEliminationSolverTest.cs index 3964f40517..03bac732b0 100644 --- a/tests/ImageSharp.Tests/Common/GaussianEliminationSolverTest.cs +++ b/tests/ImageSharp.Tests/Common/GaussianEliminationSolverTest.cs @@ -9,7 +9,7 @@ public class GaussianEliminationSolverTest { [Theory] [MemberData(nameof(MatrixTestData))] - public void CanSolve(float[][] matrix, float[] result, float[] expected) + public void CanSolve(double[][] matrix, double[] result, double[] expected) { GaussianEliminationSolver.Solve(matrix, result); @@ -19,44 +19,44 @@ public class GaussianEliminationSolverTest } } - public static TheoryData MatrixTestData + public static TheoryData MatrixTestData { get { - TheoryData data = []; + TheoryData data = []; { - float[][] matrix = + double[][] matrix = [ [2, 3, 4], [1, 2, 3], [3, -4, 0], ]; - float[] result = [6, 4, 10]; - float[] expected = [18 / 11f, -14 / 11f, 18 / 11f]; + double[] result = [6, 4, 10]; + double[] expected = [18 / 11f, -14 / 11f, 18 / 11f]; data.Add(matrix, result, expected); } { - float[][] matrix = + double[][] matrix = [ [1, 4, -1], [2, 5, 8], [1, 3, -3], ]; - float[] result = [4, 15, 1]; - float[] expected = [1, 1, 1]; + double[] result = [4, 15, 1]; + double[] expected = [1, 1, 1]; data.Add(matrix, result, expected); } { - float[][] matrix = + double[][] matrix = [ [-1, 0, 0], [0, 1, 0], [0, 0, 1], ]; - float[] result = [1, 2, 3]; - float[] expected = [-1, 2, 3]; + double[] result = [1, 2, 3]; + double[] expected = [-1, 2, 3]; data.Add(matrix, result, expected); }