Browse Source

Reformatting of Vector.Norm and Vector.Normalize code.

la-knuth
Jurgen Van Gael 16 years ago
parent
commit
37bd9b67de
  1. 85
      src/Numerics/LinearAlgebra/Double/DenseVector.cs
  2. 4
      src/Numerics/LinearAlgebra/Double/Matrix.Arithmetic.cs
  3. 29
      src/Numerics/LinearAlgebra/Double/SparseVector.cs
  4. 89
      src/Numerics/LinearAlgebra/Double/Vector.cs
  5. 4
      src/UnitTests/LinearAlgebraTests/Double/MatrixTests.Arithmetic.cs
  6. 13
      src/UnitTests/LinearAlgebraTests/Double/VectorTests.Norm.cs

85
src/Numerics/LinearAlgebra/Double/DenseVector.cs

@ -1195,75 +1195,52 @@ namespace MathNet.Numerics.LinearAlgebra.Double
#region Vector Norms
/// <summary>
/// Euclidean Norm also known as 2-Norm.
/// </summary>
/// <returns>Scalar <c>ret = sqrt(sum(this[i]^2))</c></returns>
public override double Norm()
{
var sum = 0.0;
for (var i = 0; i < Data.Length; i++)
{
sum = SpecialFunctions.Hypotenuse(sum, Data[i]);
}
return sum;
}
/// <summary>
/// 1-Norm also known as Manhattan Norm or Taxicab Norm.
/// </summary>
/// <returns>Scalar <c>ret = sum(abs(this[i]))</c></returns>
public override double Norm1()
{
return CommonParallel.Aggregate(
0,
Count,
index => Math.Abs(Data[index]));
}
/// <summary>
/// Computes the p-Norm.
/// </summary>
/// <param name="p">The p value.</param>
/// <returns>Scalar <c>ret = (sum(abs(this[i])^p))^(1/p)</c></returns>
public override double NormP(int p)
public override double Norm(double p)
{
if (1 > p)
if (p < 0.0)
{
throw new ArgumentOutOfRangeException("p");
}
if (1 == p)
else if (1.0 == p)
{
return Norm1();
return CommonParallel.Aggregate(
0,
Count,
index => Math.Abs(Data[index]));
}
if (2 == p)
else if (2.0 == p)
{
return Norm();
}
var sum = 0.0;
var sum = CommonParallel.Aggregate(
0,
Count,
index => Math.Pow(Math.Abs(Data[index]), p));
for (var i = 0; i < Data.Length; i++)
{
sum = SpecialFunctions.Hypotenuse(sum, Data[i]);
}
return Math.Pow(sum, 1.0 / p);
}
return sum;
}
else if (Double.IsPositiveInfinity(p))
{
return CommonParallel.Select(
0,
Count,
(index, localData) => localData = Math.Max(localData, Math.Abs(Data[index])),
Math.Max);
}
else
{
var sum = CommonParallel.Aggregate(
0,
Count,
index => Math.Pow(Math.Abs(Data[index]), p));
/// <summary>
/// Infinity Norm.
/// </summary>
/// <returns>Scalar <c>ret = max(abs(this[i]))</c></returns>
public override double NormInfinity()
{
return CommonParallel.Select(
0,
Count,
(index, localData) => localData = Math.Max(localData, Math.Abs(Data[index])),
Math.Max);
return Math.Pow(sum, 1.0 / p);
}
}
#endregion

4
src/Numerics/LinearAlgebra/Double/Matrix.Arithmetic.cs

@ -948,7 +948,7 @@ namespace MathNet.Numerics.LinearAlgebra.Double
i =>
{
var coli = Column(i);
var norm = coli.NormP(p);
var norm = coli.Norm(p);
for (var j = 0; j < RowCount; j++)
{
ret[j, i] = coli[j] / norm;
@ -977,7 +977,7 @@ namespace MathNet.Numerics.LinearAlgebra.Double
j =>
{
var rowj = Row(j);
var norm = rowj.NormP(p);
var norm = rowj.Norm(p);
for (var i = 0; i < RowCount; i++)
{
ret[i, j] = rowj[j] / norm;

29
src/Numerics/LinearAlgebra/Double/SparseVector.cs

@ -1296,28 +1296,25 @@ namespace MathNet.Numerics.LinearAlgebra.Double
/// </summary>
/// <param name="p">The p value.</param>
/// <returns>Scalar <c>ret = (sum(abs(this[i])^p))^(1/p)</c></returns>
public override double NormP(int p)
public override double Norm(double p)
{
if (1 > p)
{
throw new ArgumentOutOfRangeException("p");
}
else if (Double.IsPositiveInfinity(p))
{
return CommonParallel.Select(0, NonZerosCount, (index, localData) => localData = Math.Max(localData, Math.Abs(_nonZeroValues[index])), Math.Max);
}
else
{
var sum = CommonParallel.Aggregate(
0,
NonZerosCount,
index => Math.Pow(Math.Abs(_nonZeroValues[index]), p));
var sum = CommonParallel.Aggregate(
0,
NonZerosCount,
index => Math.Pow(Math.Abs(_nonZeroValues[index]), p));
return Math.Pow(sum, 1.0 / p);
}
/// <summary>
/// Infinity Norm.
/// </summary>
/// <returns>Scalar <c>ret = max(abs(this[i]))</c></returns>
public override double NormInfinity()
{
return CommonParallel.Select(0, NonZerosCount, (index, localData) => localData = Math.Max(localData, Math.Abs(_nonZeroValues[index])), Math.Max);
return Math.Pow(sum, 1.0 / p);
}
}
#endregion

89
src/Numerics/LinearAlgebra/Double/Vector.cs

@ -1112,40 +1112,6 @@ namespace MathNet.Numerics.LinearAlgebra.Double
#region Vector Norms
/// <summary>
/// Euclidean Norm also known as 2-Norm.
/// </summary>
/// <returns>
/// <c>Scalar ret = sqrt(sum(this[i]^2))</c>
/// </returns>
public virtual double Norm()
{
return NormP(2);
}
/// <summary>
/// Squared Euclidean 2-Norm.
/// </summary>
/// <returns>
/// <c>Scalar ret = sum(this[i]^2)</c>
/// </returns>
public virtual double SquaredNorm()
{
var norm = Norm();
return norm * norm;
}
/// <summary>
/// 1-Norm also known as Manhattan Norm or Taxicab Norm.
/// </summary>
/// <returns>
/// <c>Scalar ret = sum(abs(this[i]))</c>
/// </returns>
public virtual double Norm1()
{
return NormP(1);
}
/// <summary>
/// Computes the p-Norm.
/// </summary>
@ -1155,45 +1121,48 @@ namespace MathNet.Numerics.LinearAlgebra.Double
/// <returns>
/// <c>Scalar ret = (sum(abs(this[i])^p))^(1/p)</c>
/// </returns>
public virtual double NormP(int p)
public virtual double Norm(double p)
{
if (1 > p)
if (p < 0.0)
{
throw new ArgumentOutOfRangeException("p");
}
else if (Double.IsPositiveInfinity(p))
{
return CommonParallel.Select(
0,
Count,
(index, localData) => localData = Math.Max(localData, Math.Abs(this[index])),
Math.Max);
}
else
{
var sum = CommonParallel.Aggregate(
0,
Count,
index => Math.Pow(Math.Abs(this[index]), p));
var sum = CommonParallel.Aggregate(
0,
Count,
index => Math.Pow(Math.Abs(this[index]), p));
return Math.Pow(sum, 1.0 / p);
return Math.Pow(sum, 1.0 / p);
}
}
/// <summary>
/// Infinity Norm.
/// Normalizes this vector to a unit vector with respect to the p-norm.
/// </summary>
/// <param name="p">
/// The p value.
/// </param>
/// <returns>
/// <c>Scalar ret = max(abs(this[i]))</c>
/// This vector normalized to a unit vector with respect to the p-norm.
/// </returns>
public virtual double NormInfinity()
public virtual Vector Normalize(double p)
{
return CommonParallel.Select(
0,
Count,
(index, localData) => localData = Math.Max(localData, Math.Abs(this[index])),
Math.Max);
}
if (p < 0.0)
{
throw new ArgumentOutOfRangeException("p");
}
/// <summary>
/// Normalizes this vector to a unit vector with respect to the Euclidean 2-Norm.
/// </summary>
/// <returns>
/// This vector normalized to a unit vector with respect to the Euclidean 2-Norm.
/// </returns>
public virtual Vector Normalize()
{
var norm = Norm();
var norm = Norm(p);
var clone = Clone();
if (norm == 0.0)
{

4
src/UnitTests/LinearAlgebraTests/Double/MatrixTests.Arithmetic.cs

@ -632,7 +632,7 @@ namespace MathNet.Numerics.UnitTests.LinearAlgebraTests.Double
for (var j = 0; j < result.ColumnCount; j++)
{
var col = result.Column(j);
Assert.AreApproximatelyEqual(1.0, col.NormP(pValue), 10e-12);
Assert.AreApproximatelyEqual(1.0, col.Norm(pValue), 10e-12);
}
}
@ -646,7 +646,7 @@ namespace MathNet.Numerics.UnitTests.LinearAlgebraTests.Double
for (var i = 0; i < matrix.RowCount; i++)
{
var row = matrix.Row(i);
Assert.AreApproximatelyEqual(1.0, row.NormP(pValue), 10e-12);
Assert.AreApproximatelyEqual(1.0, row.Norm(pValue), 10e-12);
}
}

13
src/UnitTests/LinearAlgebraTests/Double/VectorTests.Norm.cs

@ -30,6 +30,7 @@
namespace MathNet.Numerics.UnitTests.LinearAlgebraTests.Double
{
using System;
using MbUnit.Framework;
public abstract partial class VectorTests
@ -38,21 +39,21 @@ namespace MathNet.Numerics.UnitTests.LinearAlgebraTests.Double
public void CanComputeNorm()
{
var vector = CreateVector(_data);
AssertHelpers.AlmostEqual(7.416198487095663, vector.Norm(), 15);
AssertHelpers.AlmostEqual(7.416198487095663, vector.Norm(2), 15);
}
[Test]
public void CanComputeNorm1()
{
var vector = CreateVector(_data);
AssertHelpers.AlmostEqual(15.0, vector.Norm1(), 15);
AssertHelpers.AlmostEqual(15.0, vector.Norm(1), 15);
}
[Test]
public void CanComputeSquareNorm()
{
var vector = CreateVector(_data);
AssertHelpers.AlmostEqual(55.0, vector.SquaredNorm(), 15);
AssertHelpers.AlmostEqual(55.0, vector.Norm(2) * vector.Norm(2), 15);
}
[Test]
@ -63,14 +64,14 @@ namespace MathNet.Numerics.UnitTests.LinearAlgebraTests.Double
public void CanComputeNormP(int p, double expected)
{
var vector = CreateVector(_data);
AssertHelpers.AlmostEqual(expected, vector.NormP(p), 15);
AssertHelpers.AlmostEqual(expected, vector.Norm(p), 15);
}
[Test]
public void CanComputeNormInfinity()
{
var vector = CreateVector(_data);
AssertHelpers.AlmostEqual(5.0, vector.NormInfinity(), 15);
AssertHelpers.AlmostEqual(5.0, vector.Norm(Double.PositiveInfinity), 15);
}
[Test]
@ -78,7 +79,7 @@ namespace MathNet.Numerics.UnitTests.LinearAlgebraTests.Double
public void CanNormalizeVector()
{
var vector = CreateVector(_data);
var result = vector.Normalize();
var result = vector.Normalize(2);
AssertHelpers.AlmostEqual(0.134839972492648, result[0], 14);
AssertHelpers.AlmostEqual(0.269679944985297, result[1], 14);
AssertHelpers.AlmostEqual(0.404519917477945, result[2], 14);

Loading…
Cancel
Save