how to create and multiply matrixes in c# - c#

Okay, so yesterday at school i was presented with a task in c#, which was create a program to build a Matrix and multiply that matrix by another one. so far i have done this:
List<List<double>> translacao = new List<List<double>>();
translacao[0][0] = 0;
translacao[0][1] = 0;
translacao[0][2] = 4;
translacao[1][0] = 0;
translacao[1][1] = 1;
translacao[1][2] = 6;
translacao[2][0] = 0;
translacao[2][1] = 0;
translacao[2][2] = 8;
I tried with normal arrays like double [,] , but my problem is always the same. From here, how can i multiply this Matrix by another ?? (I know how to multiply matrixes (in paper) but isnt there any method in c# that does that for me ?) the only Matrix classes i found were only able to multiply 3x3 matrixes.

I would say you are gonna have to write your own funciton, maybe even a few overloads for different sizes depending on how crafty your function is.
I am not very good at matrix math but here is somewhat of a process
also this is not c#:
matrix Multiply[][] (matrix a[][], matrix b[][])
{
//check the sizes, i remeber its something that must be done but dont remember the specifics
if (a.width != b.height)
throw WrongSizeException;
matrix result[][];
//do the math:
result[0][0] = a[0][0] * b[0][0]; //again, I don't remeber this stuff
...
...
return result;
}
I hope this gets the right gears turning

Related

An algorithm for Generating Random Holes on a grid

I'm trying to make an "Explosion effect on a grid", and I need an algorithm that will allow me to do the following:
Note: The grid represents a List<List>, and I'm trying to filter out the red dots
So we start off with a given grid with black dots (in our case, black dots represent solid points on our grid, and red dots represent the points we remove from the list)
Eventually, our ractangle transformed into this random shape with holes on the edges (blue area)
My Attempt:
The Problem:
Sometimes the radius of my star/circle shape is pretty big and the output doesn't give me that "explosion" effect I'm looking for (basically, an unpredictable output), plus it really limits the shape.
Do you have any ideas or know of some mathematical algorithms that can help? Thanks for reading! :)
Sorry if I wasn't clear enough, but this is basically what I'm looking for:
This is straightforward approach to get template:
using System;
namespace ConsoleApp2
{
class Program
{
static void Main(string[] args)
{
int size = 10;
var grid = GetExplosionTemplate(size, new Random(),1);
for (int i = 0; i < size; i++)
{
for (int j = 0; j < size; j++)
{
Console.Write(grid[i + j * size] ? "X" : "O");
}
Console.WriteLine();
}
}
private static bool[] GetExplosionTemplate(int size, Random rnd = null, float explosionRoughness = 0)
{
var grid = new bool[size * size];
var rr = (size + 1) / 2f;
for (int i = 0; i < size; i++)
{
for (int j = 0; j < size; j++)
{
var cellId = i + j * size;
var r = Math.Sqrt(Math.Pow(i - size / 2, 2) + Math.Pow(j - size / 2, 2)) + rnd?.NextDouble()*explosionRoughness ?? 0;
grid[cellId] = r > rr;
}
}
return grid;
}
}
}
Roughness above 1 will give scattered inside explosion, below will give more round explosion. Value around 0.5 to 1.5 is great looking for both even/non-even values. You can play around to make it better looking, honestly for explosion physics I rather choose this roughness based on material in cell (sand penetration is better than stone, for example), cause you don't want fully fledged physics where you calculate explosion power traveling across weighted by resistance cells (for example, explosion in cave will travel along empty paths and slightly destruct environment, rather than create vacuum in radius)
Another simple approach to actually simulate explosion physics is to use recursion. You start at center with explosion power equal to some value, than as you travel wide, each cell will consume some part of that power (and may be destroyed in process), than equaly emits left part of its power to adjacent cells (even visited, so you simulate explosion wave). This way it will be more realistic in terms of materials. You can even simulate partially empty cell from resistance materials (like, iron fence, it is resistant but emits better and destroy everything around)

How to filter values in a point array

I have a constantly feeding point array with a length of 4, and want to filter certain "outliers" in the array.
I'm creating a VR/AR app with Opencvforunity and Unity.
Using a live feed from the webcam, I have an 4-length points array which updates and contains x, y 2d coordinates, representing the four corners of a tracked object. And I'm using them as source values to draw a Rect in unity.
Each slot in array contains data such as this:
{296.64151, 88.096649}
However, Unity throws errors and crashes when the a value in the array has
negative values (sometimes happens because of tracking error)
large values exceeding the canvas size (same reason, currently using 1280 x 720)
An example of a "bad value" will be like this :
{-1745.10614, 46.908913} <- negative / big value on X
{681.00519, 1234.15828} <- big value on Y
So I have to somehow create a filter for the array to make the app to work.
The order should not be altered and the data constantly updates so ignoring/skipping bad values will be optimal. I'm new to C# and I have searched but no good luck for "point array"
Here's my code:
Point[] ptsArray = patternTrackingInfo.points2d.toArray();
pt1 = ptsArray[0];
pt2 = ptsArray[2];
pt3 = new OpenCVForUnity.CoreModule.Point(ptsArray[2].x + 5, ptsArray[2].y + 5);
for (int i = 0; i < 4; i++)
{
cropRect = new OpenCVForUnity.CoreModule.Rect(pt1, pt3);
}
pt1 represents the left-top corner and pt2 for right-bottom.
I heard that the right bottom point is exclusive in OpenCV itself so I tried to add a new point to that(pt3), but still crashing - so I believe it is not related to that matter.
Any suggestions for creating a filter for a point array will be very much helpful. Thank you.
I would just create a new list of Points and loop through the existing list, adding only the valid points to the new list. Then that becomes the list that you convert to an array for your OpenCV calls.
List<Point> filteredList = new List<Point>();
for(int i = 0; i < patternTrackingInfo.points2d.Count; i++)
{
if(/*Do your check here*/)
continue;
filteredList.Add(patternTrackingInfo.points2d[i]);
}
Point[] ptsArray = filteredList.toArray();
pt1 = ptsArray[0];
pt2 = ptsArray[2];
pt3 = new OpenCVForUnity.CoreModule.Point(ptsArray[2].x + 5, ptsArray[2].y + 5);
for (int i = 0; i < 4; i++)
{
cropRect = new OpenCVForUnity.CoreModule.Rect(pt1, pt3);
}

Confused on Clipper in C#

I'm creating a 2D game in Unity which has procedurally placed tiles. I want to simplify the collision geometry using Angus Johnson's Clipper library (specifically the union function), but I'm running into an issue with the library returning empty solutions and I'm not sure why.
For reference, here are the Polygon Colliders I've been using to test.
And here is a simplified version of the function I'm using to combine the geometry:
List<List<Vector2>> unitedPolygons = new List<List<Vector2>>();
Clipper clipper = new Clipper();
Paths solution = new Paths();
ClipperOffset offset = new ClipperOffset();
//Use a scaling factor for floats and convert the Polygon Colliders' points to Clipper's desired format
int scalingFactor = 10000;
for (int i = 0; i < polygons.Count; i++)
{
Path allPolygonsPath = new Path(polygons[i].points.Length);
for (int j = 0; j < polygons[i].points.Length; j++)
{
allPolygonsPath.Add(new IntPoint(Mathf.Floor(polygons[i].points[j].x * scalingFactor), Mathf.Floor(polygons[i].points[j].y * scalingFactor)));
}
bool succeeded = clipper.AddPath(allPolygonsPath, PolyType.ptSubject, true);
}
//Execute the union
bool success = clipper.Execute(ClipType.ctUnion, solution);
Debug.Log("Polygons after union: " + solution.Count);
//Offset the polygons
offset.AddPaths(solution, JoinType.jtMiter, EndType.etClosedPolygon);
offset.Execute(ref solution, 5f);
//Convert back to a format Unity can use
foreach (Path path in solution)
{
List<Vector2> unitedPolygon = new List<Vector2>();
foreach (IntPoint point in path)
{
unitedPolygon.Add(new Vector2(point.X / (float)scalingFactor, point.Y / (float)scalingFactor));
}
unitedPolygons.Add(unitedPolygon);
}
return unitedPolygons;
What I've discovered through debugging is that the first Execute (for the union) is returning an empty solution. I've figured out that the "BuildResult" function in the "Clipper" class is indeed running, and "m_PolyOuts" has data in it, but the "Pts" property of the "OutRec"s in that list are all null. I can't figure out where this happens or if they were ever set in the first place.
I'm convinced this is proper behavior and I'm just using the library wrong, but I can't find any documentation or examples explaining what I need to change to make the union succeed.
Thanks.
EDIT: I've narrowed it down a bit more. During "ExecuteInteral" in the Clipper class, the "Pts" lists aren't null until the "FixupOutPolygon" function is run. After that, all of the lists are null. "JoinCommonEdges" also makes a couple of the lists null, but not all of them.
I've been working on my own game project as well and stumbled upon similar problem with Clipper. What worked for me in this case was instead of writing this:
clipper.Execute(ClipType.ctUnion, solution);
... I specified PolyFillType for Execute method:
clipper.Execute(ClipType.ctUnion, solution, PolyFillType.pftNonZero, PolyFillType.pftNonZero);
I'm not sure why it worked for me but I think it's due to the fact that some Paths can share common edges so with the default pftEvenOdd filling rule it gets cut out.

Accord.Net Get equation of the SVM model

I have been testing the sample Kernel Support Vector Machines for regression problems and I would like to know how do you get the equation of the model.
For example, if the machine is created using a polynomial kernel (degree = 1), how do you get the line equation (mx + b) of this model. Is there any method in the SupportVectorMachine Class to get the model equation? or is there any way to calculate the parameters of the equation from the variables obtained after the machine is created.
Thanks in advance.
Looks like you can use this method below:
ToWeights(), which
Converts a Linear-kernel machine into an array of linear coefficients.
The first position in the array is the Threshold value.
So in your language, the first position in the array is the bias b and the rest are your linear coefficients m.
I got weird coefficients from ToWeights() when using SequentialMinimalOptimization() from which I couldn't derive the hyperplane equation. Using LinearCoordinateDescent() yielded usable coefficients for the model, however, in the form of [a,b,c...] which could be plugged in as 0 = a + bx + cy + ...
Hope that helps!
As #zrolfs noted, if you are using Accord.NET with Sequential Minimal Optimization, the ToWeights() function does not currently return relevant coefficients for the decision function. Nevertheless, you can calculate these coefficients directly. In order to do so, multiply the SVM weights vector by the matrix of support vectors, like so:
double[] DecisionFunctionCoefficients = new double[dwTotalFeatures];
for (int iFeature = 0; iFeature < dwTotalFeatures; iFeature++) {
for (int iVector = 0; iVector < SVM.SupportVectors.Length; iVector++) {
DecisionFunctionCoefficients[iFeature] += (SVM.SupportVectors[iVector][iFeature] * SVM.Weights[iVector]);
}
}

Discrete Fourier transform

I am currently trying to write some fourier transform algorithm. I started with a simple DFT algorithm as described in the mathematical definition:
public class DFT {
public static Complex[] Transform(Complex[] input) {
int N = input.Length;
Complex[] output = new Complex[N];
double arg = -2.0 * Math.PI / (double)N;
for (int n = 0; n < N; n++) {
output[n] = new Complex();
for (int k = 0; k < N; k++)
output[n] += input[k] * Complex.Polar(1, arg * (double)n * (double)k);
}
return output;
}
}
So I tested this algorithm with the following code:
private int samplingFrequency = 120;
private int numberValues = 240;
private void doCalc(object sender, EventArgs e) {
Complex[] input = new Complex[numberValues];
Complex[] output = new Complex[numberValues];
double t = 0;
double y = 0;
for (int i = 0; i < numberValues; i++) {
t = (double)i / (double)samplingFrequency;
y = Math.Sin(2 * Math.PI * t);
input[i] = new Complex(y, 0);
}
output = DFT.Transform(input);
printFunc(input);
printAbs(output);
}
The transformation works fine, but only if numberValues is a multiple number of the samplingFrequency (in this case: 120, 240, 360,...). Thats my result for 240 values:
The transformation just worked fine.
If i am trying to calculate 280 values I get this result:
Why I am getting a incorrect result if I change the number of my calculated values?
I am not sure if my problem here is a problem with my code or a misunderstanding of the mathematical definition of the DFT. In either way, can anybody help me with my problem? Thanks.
What you are experiencing is called Spectral Leakage.
This is caused because the underlying mathematics of the Fourier transform assumes a continuous function from -infinity to + infinity. So the range of samples you provide is effectively repeated an infinite number of times. If you don't have a complete number of cycles of the waveform in the window the ends won't line up and you will get a discontinuity which manifests its self as the frequency smearing out to either side.
The normal way to handle this is called Windowing. However, this does come with a downside as it causes the amplitudes to be slightly off. This is the process of multiply the whole window of samples you are going to process by some function which tends towards 0 at both ends of the window causing the ends to line up but with some amplitude distortion because this process lowers the total signal power.
So to summarise there is no error in your code, and the result is as expected. The artefacts can be reduced using a window function, however this will effect the accuracy of the amplitudes. You will need to investigate and determine what solution best fits the requirements of your project.
You are NOT getting the incorrect result for a non-periodic sinusoid. And they are not just "artifacts". Your result is actually the more complete DFT result which you don't see with a periodic sinusoid. Those other non-zero values contain useful information which can be used to, for example, interpolate the frequency of a single non-periodic-in-aperture sinusoid.
A DFT can be thought of as convolving a rectangular window with your sine wave. This produces (something very close to) a Sinc function, which has infinite extent, BUT just happens to be zero at every DFT bin frequency other than its central DFT bin for any sinusoid centered exactly on a DFT bin. This happens only when the frequency is exactly periodic in the FFT aperture, not for any other. The Sinc function has lots of "humps" which are all hidden in your first plot.

Categories

Resources