mirror of https://github.com/emgucv/emgucv.git
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
483 lines
17 KiB
483 lines
17 KiB
//----------------------------------------------------------------------------
|
|
// Copyright (C) 2004-2020 by EMGU Corporation. All rights reserved.
|
|
//----------------------------------------------------------------------------
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using System.Diagnostics;
|
|
using System.Drawing;
|
|
using System.IO;
|
|
using System.Runtime.InteropServices;
|
|
using System.Runtime.Serialization;
|
|
using System.Text;
|
|
using System.Threading;
|
|
using System.Xml;
|
|
using System.Xml.Linq;
|
|
using Emgu.CV;
|
|
using Emgu.CV.Structure;
|
|
using Emgu.Util;
|
|
|
|
|
|
#if VS_TEST
|
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
|
using TestAttribute = Microsoft.VisualStudio.TestTools.UnitTesting.TestMethodAttribute;
|
|
using TestFixture = Microsoft.VisualStudio.TestTools.UnitTesting.TestClassAttribute;
|
|
#elif NETFX_CORE
|
|
using Microsoft.VisualStudio.TestPlatform.UnitTestFramework;
|
|
using TestAttribute = Microsoft.VisualStudio.TestPlatform.UnitTestFramework.TestMethodAttribute;
|
|
using TestFixture = Microsoft.VisualStudio.TestPlatform.UnitTestFramework.TestClassAttribute;
|
|
#else
|
|
using NUnit.Framework;
|
|
#endif
|
|
|
|
namespace Emgu.CV.Test
|
|
{
|
|
[TestFixture]
|
|
public class AutoTestMatrix
|
|
{
|
|
[Test]
|
|
public void TestInvert()
|
|
{
|
|
Matrix<Single> m = new Matrix<Single>(3, 3);
|
|
Matrix<Single> mInvert = new Matrix<Single>(3, 3);
|
|
|
|
m.SetIdentity();
|
|
|
|
CvInvoke.Invert(m, mInvert, Emgu.CV.CvEnum.DecompMethod.LU);
|
|
|
|
EmguAssert.IsTrue(m.Equals(mInvert));
|
|
}
|
|
|
|
[Test]
|
|
public void TestGetData()
|
|
{
|
|
float[,] data = new float[2, 3];
|
|
data[0, 0] = 1; data[0, 1] = 2; data[0, 2] = 3;
|
|
data[1, 0] = 4; data[1, 1] = 5; data[1, 2] = 6;
|
|
GCHandle dataHandle = GCHandle.Alloc(data, GCHandleType.Pinned);
|
|
using (Matrix<float> m = new Matrix<float>(data.GetLength(0), data.GetLength(1), dataHandle.AddrOfPinnedObject()))
|
|
{
|
|
float[,] data2 = m.Data;
|
|
for (int i = 0; i < data2.GetLength(0); i++)
|
|
for (int j = 0; j < data.GetLength(1); j++)
|
|
EmguAssert.IsTrue(data2[i, j] == data[i, j]);
|
|
}
|
|
|
|
dataHandle.Free();
|
|
}
|
|
|
|
|
|
[Test]
|
|
public void TestSolve()
|
|
{
|
|
Matrix<Single> lhs = new Matrix<Single>(3, 3);
|
|
lhs.SetIdentity();
|
|
Matrix<Single> rhs = new Matrix<Single>(new float[,] { { 0.1f }, { 0.2f }, { 0.5f } });
|
|
Matrix<Single> result = new Matrix<float>(3, 1);
|
|
CvInvoke.Solve(lhs, rhs, result, CvEnum.DecompMethod.LU);
|
|
|
|
EmguAssert.AreEqual(rhs[0, 0], result[0, 0]);
|
|
EmguAssert.AreEqual(rhs[1, 0], result[1, 0]);
|
|
EmguAssert.AreEqual(rhs[2, 0], result[2, 0]);
|
|
}
|
|
|
|
[Test]
|
|
public void TestNot()
|
|
{
|
|
Matrix<byte> m = new Matrix<byte>(10, 8);
|
|
m.SetValue(1.0);
|
|
m._Not();
|
|
byte[,] d2 = m.Data;
|
|
|
|
foreach (byte v in d2)
|
|
EmguAssert.IsTrue(254.0 == v);
|
|
}
|
|
|
|
[Test]
|
|
public void TestArithmatic()
|
|
{
|
|
Matrix<byte> m = new Matrix<byte>(10, 8);
|
|
m.SetRandNormal(new MCvScalar(), new MCvScalar(30));
|
|
Matrix<byte> mMultiplied = m.Mul(2.0);
|
|
|
|
for (int i = 0; i < m.Rows; i++)
|
|
for (int j = 0; j < m.Cols; j++)
|
|
EmguAssert.IsTrue(m[i, j] * 2 == mMultiplied[i, j]);
|
|
}
|
|
|
|
[Test]
|
|
public void TestCvInvoke()
|
|
{
|
|
IntPtr mat = CvInvoke.cvCreateMat(10, 10, Emgu.CV.CvEnum.DepthType.Cv32F);
|
|
CvInvoke.cvReleaseMat(ref mat);
|
|
mat = CvInvoke.cvCreateMat(10, 10, Emgu.CV.CvEnum.DepthType.Cv32S);
|
|
CvInvoke.cvReleaseMat(ref mat);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Test the matrix constructor that accepts a two dimensional array as input
|
|
/// </summary>
|
|
[Test]
|
|
public void TestData()
|
|
{
|
|
Byte[,] data = new Byte[20, 30];
|
|
Random r = new Random();
|
|
Byte[] bytes = new Byte[data.Length];
|
|
r.NextBytes(bytes);
|
|
for (int i = 0; i < data.GetLength(0); i++)
|
|
for (int j = 0; j < data.GetLength(1); j++)
|
|
data[i, j] = bytes[i * data.GetLength(1) + j];
|
|
|
|
Matrix<Byte> m = new Matrix<byte>(data);
|
|
Byte[,] data2 = m.Data;
|
|
|
|
for (int i = 0; i < data.GetLength(0); i++)
|
|
for (int j = 0; j < data.GetLength(1); j++)
|
|
{
|
|
EmguAssert.AreEqual(data[i, j], data2[i, j]);
|
|
EmguAssert.AreEqual(data[i, j], m[i, j]);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Test the matrix transpose function for matrix of Byte
|
|
/// </summary>
|
|
[Test]
|
|
public void TestTransposeByteMatrix()
|
|
{
|
|
using (Matrix<Byte> mat = new Matrix<Byte>(1, 10))
|
|
{
|
|
mat.SetRandUniform(new MCvScalar(0.0), new MCvScalar(255.0));
|
|
|
|
Matrix<Byte> matT = mat.Transpose();
|
|
|
|
for (int i = 0; i < matT.Rows; i++)
|
|
for (int j = 0; j < matT.Cols; j++)
|
|
EmguAssert.AreEqual(matT[i, j], mat[j, i]);
|
|
}
|
|
}
|
|
|
|
[Test]
|
|
public void TestTransposeFloatMatrix()
|
|
{
|
|
using (Matrix<float> mat = new Matrix<float>(1, 3))
|
|
{
|
|
mat.SetRandUniform(new MCvScalar(-1000.0), new MCvScalar(1000.0));
|
|
|
|
Matrix<float> matT = mat.Transpose();
|
|
|
|
for (int i = 0; i < matT.Rows; i++)
|
|
for (int j = 0; j < matT.Cols; j++)
|
|
EmguAssert.AreEqual(matT[i, j], mat[j, i]);
|
|
}
|
|
}
|
|
|
|
[Test]
|
|
public void TestGetDiagColRow()
|
|
{
|
|
Matrix<double> m = new Matrix<double>(new double[,] { { 1, 2 }, { 3, 4 } });
|
|
Matrix<double> diag = m.GetDiag();
|
|
EmguAssert.IsTrue(diag[0, 0] == 1);
|
|
EmguAssert.IsTrue(diag[1, 0] == 4);
|
|
EmguAssert.IsTrue(diag.Sum == m.Trace.V0);
|
|
|
|
Matrix<double> col1 = m.GetCol(1);
|
|
EmguAssert.IsTrue(col1[0, 0] == 2);
|
|
EmguAssert.IsTrue(col1[1, 0] == 4);
|
|
EmguAssert.IsTrue(col1.Sum == 2 + 4);
|
|
|
|
Matrix<double> row1 = m.GetRow(1);
|
|
EmguAssert.IsTrue(row1[0, 0] == 3);
|
|
EmguAssert.IsTrue(row1[0, 1] == 4);
|
|
EmguAssert.IsTrue(row1.Sum == 3 + 4);
|
|
}
|
|
|
|
[Test]
|
|
public void TestXmlSerializeAndDeserialize()
|
|
{
|
|
using (Matrix<Byte> mat = new Matrix<byte>(50, 60))
|
|
{
|
|
mat.SetRandUniform(new MCvScalar(0), new MCvScalar(255));
|
|
|
|
#if !WINDOWS_PHONE_APP
|
|
XDocument doc = Toolbox.XmlSerialize<Matrix<Byte>>(mat);
|
|
//Trace.WriteLine(doc.OuterXml);
|
|
|
|
using (Matrix<Byte> mat2 = Toolbox.XmlDeserialize<Matrix<Byte>>(doc))
|
|
EmguAssert.IsTrue(mat.Equals(mat2));
|
|
#endif
|
|
}
|
|
}
|
|
|
|
#if !NETFX_CORE
|
|
[Test]
|
|
public void TestRuntimeSerialize1()
|
|
{
|
|
Matrix<Byte> mat = new Matrix<Byte>(100, 80, 2);
|
|
mat.SetRandNormal(new MCvScalar(100, 100, 100), new MCvScalar(50, 50, 50));
|
|
|
|
System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
|
|
formatter = new System.Runtime.Serialization.Formatters.Binary.BinaryFormatter();
|
|
|
|
Byte[] bytes;
|
|
using (MemoryStream ms = new MemoryStream())
|
|
{
|
|
formatter.Serialize(ms, mat);
|
|
bytes = ms.GetBuffer();
|
|
}
|
|
using (MemoryStream ms2 = new MemoryStream(bytes))
|
|
{
|
|
Matrix<Byte> mat2 = (Matrix<Byte>)formatter.Deserialize(ms2);
|
|
EmguAssert.IsTrue(mat.Equals(mat2));
|
|
}
|
|
}
|
|
|
|
[Test]
|
|
public void TestRuntimeSerialize2()
|
|
{
|
|
Random r = new Random();
|
|
double[,,] data = new double[100, 80, 2];
|
|
for (int i = 0; i < data.GetLength(0); i++)
|
|
for (int j = 0; j < data.GetLength(1); j++)
|
|
for (int k = 0; k < data.GetLength(2); k++)
|
|
data[i, j, k] = r.NextDouble();
|
|
|
|
GCHandle handle = GCHandle.Alloc(data, GCHandleType.Pinned);
|
|
|
|
Matrix<Double> mat = new Matrix<Double>(data.GetLength(0), data.GetLength(1), data.GetLength(2), handle.AddrOfPinnedObject(), sizeof(double) * data.GetLength(1) * data.GetLength(2));
|
|
|
|
System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
|
|
formatter = new System.Runtime.Serialization.Formatters.Binary.BinaryFormatter();
|
|
|
|
Byte[] bytes;
|
|
using (MemoryStream ms = new MemoryStream())
|
|
{
|
|
formatter.Serialize(ms, mat);
|
|
bytes = ms.GetBuffer();
|
|
}
|
|
using (MemoryStream ms2 = new MemoryStream(bytes))
|
|
{
|
|
Matrix<Double> mat2 = (Matrix<double>)formatter.Deserialize(ms2);
|
|
EmguAssert.IsTrue(mat.Equals(mat2));
|
|
}
|
|
handle.Free();
|
|
}
|
|
|
|
[Test]
|
|
public void TestRuntimeSerialize3()
|
|
{
|
|
MCvPoint3D32f[] data = new MCvPoint3D32f[] { new MCvPoint3D32f() };
|
|
|
|
GCHandle handle = GCHandle.Alloc(data, GCHandleType.Pinned);
|
|
|
|
Matrix<float> mat = new Matrix<float>(data.GetLength(0), 1, 3, handle.AddrOfPinnedObject(), sizeof(float) * 3);
|
|
|
|
System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
|
|
formatter = new System.Runtime.Serialization.Formatters.Binary.BinaryFormatter();
|
|
|
|
Byte[] bytes;
|
|
using (MemoryStream ms = new MemoryStream())
|
|
{
|
|
formatter.Serialize(ms, mat);
|
|
bytes = ms.GetBuffer();
|
|
}
|
|
using (MemoryStream ms2 = new MemoryStream(bytes))
|
|
{
|
|
Matrix<float> mat2 = (Matrix<float>)formatter.Deserialize(ms2);
|
|
EmguAssert.IsTrue(mat.Equals(mat2));
|
|
}
|
|
handle.Free();
|
|
}
|
|
#endif
|
|
|
|
#if !WINDOWS_PHONE_APP //bad garbage collector in Windows phone results in failed test?
|
|
[Test]
|
|
public void TestStressTestMatrixGC()
|
|
{
|
|
int i = 0;
|
|
//try
|
|
{
|
|
for (i = 0; i < 500; i++)
|
|
{
|
|
Matrix<Single> mat = new Matrix<float>(500, 500);
|
|
//Thread.Sleep(5);
|
|
}
|
|
}
|
|
//catch (Exception)
|
|
{
|
|
}
|
|
//finally
|
|
{
|
|
//Trace.WriteLine(i);
|
|
}
|
|
}
|
|
#endif
|
|
|
|
[Test]
|
|
public void TestSubMatrix()
|
|
{
|
|
Matrix<float> mat = new Matrix<float>(30, 40);
|
|
mat.SetRandUniform(new MCvScalar(0), new MCvScalar(255));
|
|
Matrix<float> submat = mat.GetSubRect(new Rectangle(5, 5, 15, 15));
|
|
for (int i = 0; i < 15; i++)
|
|
for (int j = 0; j < 15; j++)
|
|
EmguAssert.AreEqual(mat[i + 5, j + 5], submat[i, j]);
|
|
|
|
Matrix<float> secondRow = mat.GetRow(1);
|
|
for (int i = 0; i < mat.Cols; i++)
|
|
{
|
|
EmguAssert.AreEqual(mat[1, i], secondRow[0, i]);
|
|
}
|
|
|
|
Matrix<float> thirdCol = mat.GetCol(2);
|
|
for (int i = 0; i < mat.Rows; i++)
|
|
{
|
|
EmguAssert.AreEqual(mat[i, 2], thirdCol[i, 0]);
|
|
}
|
|
|
|
Matrix<float> diagonal = mat.GetDiag();
|
|
for (int i = 0; i < Math.Min(mat.Rows, mat.Cols); i++)
|
|
{
|
|
EmguAssert.AreEqual(diagonal[i, 0], mat[i, i]);
|
|
}
|
|
}
|
|
|
|
[Test]
|
|
public void TestMinMax()
|
|
{
|
|
Matrix<float> mat = new Matrix<float>(30, 40);
|
|
mat.SetRandUniform(new MCvScalar(0), new MCvScalar(255));
|
|
double min, max;
|
|
Point minLoc, maxLoc;
|
|
mat.MinMax(out min, out max, out minLoc, out maxLoc, null);
|
|
}
|
|
|
|
[Test]
|
|
public void TestMinMax2()
|
|
{
|
|
Matrix<Single> matrix = new Matrix<Single>(10, 10);
|
|
matrix.SetValue(5);
|
|
matrix[5, 5] = 10;
|
|
matrix[3, 3] = 0;
|
|
|
|
double minVal = 5;
|
|
double maxVal = 5;
|
|
Point minLoc = new Point();
|
|
Point maxLoc = new Point();
|
|
|
|
matrix.MinMax(out minVal, out maxVal, out minLoc, out maxLoc);
|
|
EmguAssert.IsTrue(minVal == 0);
|
|
EmguAssert.IsTrue(maxVal == 10);
|
|
EmguAssert.IsTrue(minLoc.Equals(new Point(3, 3)));
|
|
EmguAssert.IsTrue(maxLoc.Equals(new Point(5, 5)));
|
|
}
|
|
|
|
[Test]
|
|
public void TestConcate()
|
|
{
|
|
Matrix<float> mat = new Matrix<float>(30, 40);
|
|
mat.SetRandUniform(new MCvScalar(0), new MCvScalar(255));
|
|
|
|
Matrix<float> m1 = mat.GetSubRect(new Rectangle(0, 0, mat.Cols, 20));
|
|
Matrix<float> m2 = mat.GetSubRect(new Rectangle(0, 20, mat.Cols, mat.Rows - 20));
|
|
Matrix<float> mat2 = m1.ConcateVertical(m2);
|
|
EmguAssert.IsTrue(mat.Equals(mat2));
|
|
|
|
Matrix<float> m3 = mat.GetSubRect(new Rectangle(0, 0, 10, mat.Rows));
|
|
Matrix<float> m4 = mat.GetSubRect(new Rectangle(10, 0, mat.Cols - 10, mat.Rows));
|
|
Matrix<float> mat3 = m3.ConcateHorizontal(m4);
|
|
EmguAssert.IsTrue(mat.Equals(mat3));
|
|
|
|
Matrix<float> m5 = mat.GetRows(0, 5, 1);
|
|
Matrix<float> m6 = mat.GetRows(5, 6, 1);
|
|
Matrix<float> m7 = mat.GetRows(6, mat.Rows, 1);
|
|
EmguAssert.IsTrue(mat.RemoveRows(5, 6).Equals(m5.ConcateVertical(m7)));
|
|
EmguAssert.IsTrue(mat.RemoveRows(0, 1).Equals(mat.GetRows(1, mat.Rows, 1)));
|
|
EmguAssert.IsTrue(mat.RemoveRows(mat.Rows - 1, mat.Rows).Equals(mat.GetRows(0, mat.Rows - 1, 1)));
|
|
}
|
|
|
|
[Test]
|
|
public void TestMultiChannelMatrix()
|
|
{
|
|
Matrix<float> m = new Matrix<float>(10, 20, 2);
|
|
m.SetRandUniform(new MCvScalar(), new MCvScalar(255, 255));
|
|
EmguAssert.AreEqual(10, m.Rows);
|
|
EmguAssert.AreEqual(20, m.Cols);
|
|
EmguAssert.AreEqual(2, m.NumberOfChannels);
|
|
|
|
#if !WINDOWS_PHONE_APP
|
|
XDocument xDoc = Toolbox.XmlSerialize<Matrix<float>>(m);
|
|
Matrix<float> m2 = Toolbox.XmlDeserialize<Matrix<float>>(xDoc);
|
|
EmguAssert.IsTrue(m.Equals(m2));
|
|
#endif
|
|
}
|
|
|
|
[Test]
|
|
public void TestEigenVV()
|
|
{
|
|
int size = 3;
|
|
Matrix<float> tmp = new Matrix<float>(size, size);
|
|
tmp.SetRandNormal(new MCvScalar(0), new MCvScalar(1));
|
|
Matrix<float> symMat = new Matrix<float>(tmp.Size);
|
|
CvInvoke.MulTransposed(tmp, symMat, false, null, 1.0, CvEnum.DepthType.Cv32S);
|
|
Matrix<float> clone = symMat.Clone();
|
|
|
|
Matrix<float> evects = new Matrix<float>(symMat.Size);
|
|
Matrix<float> evals = new Matrix<float>(symMat.Rows, 1);
|
|
CvInvoke.Eigen(symMat, evals, evects);
|
|
}
|
|
|
|
[Test]
|
|
public void TestSparseMatrix()
|
|
{
|
|
int[] dimension = new int[2];
|
|
dimension[0] = 1000000;
|
|
dimension[1] = 1000000;
|
|
//without sparase matrix, a matrix of this size is almost impossible to create in memory
|
|
|
|
using (SparseMatrix<double> m1 = new SparseMatrix<double>(dimension))
|
|
{
|
|
m1[3, 10009] = 2.0;
|
|
EmguAssert.AreEqual(2.0, m1[3, 10009]);
|
|
}
|
|
}
|
|
|
|
[Test]
|
|
public void TestMatrixSubtract()
|
|
{
|
|
Matrix<float> f = new Matrix<float>(600, 480);
|
|
//set the value to 300
|
|
f.SetValue(new MCvScalar(300));
|
|
f -= 10;
|
|
using (ScalarArray sa = new ScalarArray(290))
|
|
using (Mat absDiff = new Mat())
|
|
{
|
|
//calculate the different of the value in f mat with 290
|
|
CvInvoke.AbsDiff(f, sa, absDiff);
|
|
int nonZeroCount = CvInvoke.CountNonZero(absDiff);
|
|
//Console.WriteLine(String.Format("number of elements that is not 290: {0}", nonZeroCount));
|
|
}
|
|
}
|
|
|
|
/*
|
|
[Test]
|
|
public void TestDataContractSerializer()
|
|
{
|
|
DataContractSerializer serializer = new DataContractSerializer(typeof(Image<Bgr, float>));
|
|
Image<Bgr, float> img1 = new Image<Bgr,float>(5, 3);
|
|
|
|
Byte[] bytes = null;
|
|
using (MemoryStream ms = new MemoryStream())
|
|
{
|
|
serializer.WriteObject(ms, img1);
|
|
bytes = ms.ToArray();
|
|
}
|
|
Image<Bgr, float> img2;
|
|
DataContractSerializer deserializer = new DataContractSerializer(typeof(Image<Bgr, float>));
|
|
using (MemoryStream ms = new MemoryStream(bytes))
|
|
{
|
|
img2 = deserializer.ReadObject(ms) as Image<Bgr, float>;
|
|
}
|
|
Debug.Assert(img1.Equals(img2));
|
|
}*/
|
|
}
|
|
}
|