IndexOutOfRangeException C# - c#

My goal is to make a triple for loop to multiply matrix X matrix, i get in input the matrix and i have to get matrix^2.
I get the error "IndexOutOfRangeException" - index was outside the bounds of the array when i debug the following code:
for (int i = 1; i < nodeList.Count+1; i++)
{
for (int j = 1; j < nodeList.Count+1; j++)
{
result[i, j] = "0";
for (int k = 1; k < nodeList.Count+1; i++)
{
if ((matrix[i, k] != null) && (matrix[k, j] != null))
{
n1 = Convert.ToInt32(matrix[i, k]);
n2 = Convert.ToInt32(matrix[k, j]);
n3 = Convert.ToInt32(result[i, j]);
total = n3 + n1 * n2;
_total = total.ToString();
result[i, j] = _total;
}
}
}
}
where the variables are:
1. matrix that is type String[,] and the dimensions are (nodelist+1,nodelist+1)
2.result that is is the same type and dimension of the matrix, where i want to put the resultant matrix
3.nodelist is the array of the names of the nodes that i have in the diagram
4. n1,n2,n3 are int, I put in them the convert int from the matrix
5.total is the result of the operation for the multiplication
6._total convert total int in total string for the result matrix
So i set the right dimensions for every array and matrix but i get constantly the same error. I don't get it why. Can please someone help to notice the error, because i don't see it.

In the k loop, you are incrementing i.

for (int k = 1; k < nodeList.Count+1; i++) <-- you are incrementing i, it should be incrementing k.
like this:
for (int k = 1; k < nodeList.Count+1; k++)

Arrays are 0-based in C# -- the first element is at position 0 instead of position 1.
for (int i = 1; i < nodeList.Count+1; i++)
... should be ...
for (int i = 0; i < nodeList.Count; i++)
You also have what appears to be a copy-paste error for the k-loop.
for (int k = 1; k < nodeList.Count+1; i++) // should be k++?

The standard way to use a for loop with an array is to use
for(int x= 0; x < arry.count ;x++)
using 1 and +1 as the conditional will assure that you get an index out of rage as c# arrays are indexed by 0

As mentioned you are incrementing by i in the K loop.
Also you will be getting the out of bounds error every time you try to access an matrix on the last iteration of the loops. Either you need to go from 0 to Count in your loops or you need to put a -1 in all of your matrix operations. ex:
results[i-1, j-1] = _total;
The matrix indexes start at 0.

Related

How to populate 2D array with char array in C#

I'm trying to fill a 2D char array with characters form a char array
I have tried this code but not finding the problem
public void FillArray(char[,] array, char[] values)
{
for (int i = 0; i < array.GetLength(0); i++)
{
for (int j = 0; j < array.GetLength(1); j++)
{
for (int k = 0; k < values.Length; k++)
{
array[i, j] = values[k];
}
}
}
}
Your first for loop is responsible for iteration over first dimension of array (i) It's okay.
Your second for loop is responsible for iteration over second dimension of array (j). It's okay.
Your third loop is responsible for iteration over char values array (k) Here's your bug.
For a given set of values of i and j which represents dimensions indexes of array, your function iterates through all positions of values array. So for each k value i and j values remain unchanged. Therefore you sequentially put all the values of values array (k+1)times into the same cell of two dimension array, ultimately leaving it with value of values[values.Length] as it is the highest possible value of k in the most nested loop.
I'd suggest solution similar to what #adv12 has proposed with slight modification as I am not sure if the k value would be 0 during first iteration of the nested for loop. It is also more readable IMO.
int k = 0;
public void FillArray(char[,] array, char[] values)
{
for (int i = 0; i < array.GetLength(0); i++)
{
for (int j = 0; j < array.GetLength(1); j++)
{
array[i, j] = values[k];
k++
if (k >= values.Length)
{
k = 0;
}
}
}
}
Here's my best guess at what you want based on your comments:
int k = 0;
public void FillArray(char[,] array, char[] values)
{
for (int i = 0; i < array.GetLength(0); i++)
{
for (int j = 0; j < array.GetLength(1); j++)
{
array[i, j] = values[k++];
if (k >= values.Length)
{
k = 0;
}
}
}
}

How to eliminate duplicates in 2D arrays in C#

just started to learn programming and I need 2D array without duplicates. This code (well edited for 1D) worked just fine for 1D but doesn't for 2D and have no clue why.
Would be very happy if someone helped me. Thanks.
Random r = new Random();
int[,] array = new int[10, 8];
for (int i = 0; i < array.GetLength(0); i++)
{
for (int j = 0; j < array.GetLength(1); j++)
{
array[i, j] = r.Next(10, 100);
for (int k = 0; k < i; k++)
{
for (int l = 0; l < j; l++)
{
if (array[i,j] == array[k,l])
{
i--;
j--;
break;
}
}
}
}
}
With the nested j loop you are filling the entire second dimension for each i, but in the k and l loops you are only checking the grid to the upper and left of current cell. You could place a number twice because you are not checking every previously filled location.
If we change the code to this:
for (int k = 0; k < array.GetLength(0); k++)
{
for (int l = 0; l < array.GetLength(1); l++)
{
if (i != k && j != l && array[i, j] == array[k, l])
{
i--;
j--;
break;
}
}
}
Then you eliminate that problem, but you very quickly find that you get a IndexOutOfRangeException because you're decrementing both i & j at the same time. That's not moving you to the previous value - it's jumping back a whole row and left one cell - and that's ultimately sending i or j to -1 and that's not good.
If you want to do it like you're attempting then you need to have a way to simply move back to the previously filled cell, regardless of the row or column you're on.
Try this:
for (int x = 0; x < array.GetLength(0) * array.GetLength(1); x++)
{
array[x % array.GetLength(0), x / array.GetLength(0)] = r.Next(10, 100);
for (int y = 0; y < x; y++)
{
if (array[x % array.GetLength(0), x / array.GetLength(0)] == array[y % array.GetLength(0), y / array.GetLength(0)])
{
x--;
break;
};
}
}
However, that's not very efficient. Try this instead:
var values = Enumerable.Range(10, 90).OrderBy(_ => r.Next()).ToArray();
for (int x = 0; x < array.GetLength(0) * array.GetLength(1); x++)
{
array[x % array.GetLength(0), x / array.GetLength(0)] = values[x];
}
So, first of all, that just seems inefficient. Not sure why you want to do it this way, but then again, don't know the reason. Looks like a programming assignment.
My guess, you need a sort of double break going on. When you break finding a match, you don't break out to the "k" for loop, so you continue looking for a match even though you found one. Try setting a boolean value to say it's found, then use that in the criteria for the for loop for k. That'll break it out and let you start over on the outside loops for i and j.
Even then, it won't work because you indescriminately subtracted i and j. So if you're on position 1,2 you will jump back to 0,1 rather than 1,2. So you need to subtract j, if it drops below 0, then subtract from i and add "array.GetLength(1)" to j.
This solution depends on HashSet's property of containing unique elements. It has an Add method that returns false when we try to add existing elements.
Random r = new Random();
int[,] array = new int[10, 8];
var usedValues = new HashSet<int>();
for (int i = 0; i < array.GetLength(0); i++)
{
for (int j = 0; j < array.GetLength(1); j++)
{
int uniqueValue;
while (true)
{
uniqueValue = r.Next(10, 100);
if (usedValues.Add(uniqueValue)) break; // It is unique indeed
// It is not unique, try again.
}
array[i, j] = uniqueValue;
}
}
The above solution is more suitable when the range of the acceptable unique values is large. In this specific case the range is very small (10-99), and the solution offered by #Enigmativity is preferable.

How can I fill a 2d array recursively?

I have a string filled with 9 numbers. I want to fill a 3x3 array with the numbers. I've managed to do it using a foreach and 2 for loops, but I feel this is quite messy. How can I modify my code to recursively enter the values into the array? This is my code currently:
int[,] matrix = new int[3, 3];
if(key.Length < 9 || key.Length > 9)
{
keyfield.GetComponent<InputField>().text = " Key Not Valid";
}
else
{
foreach(char c in key)
{
for (int k = 0; k < 3; k++)
{
for (int j = 0; j < 3; j++)
{
matrix[j, k] = c - 0;
}
}
}
}
Note, I'm working with Unity.
Well, just iterate over the chars in your key and assign them to the array, one field at a time. It's just a matter of calculating the correct columns and rows:
for (int i = 0; i < 9; ++i)
{
int row = i / 3;
int col = i % 3;
matrix[row, col] = (int)key[i];
}
Also note that neither the code in your question nor the code in my answer solves the problem in a recursive way. Recursion is given when a method calls itself directly or indirectly, which is not required to solve this particular problem.

C#:How can I compare between the sum of every row in 2D array?

I would like to know how can I check if the sum of every row in 2D array is equal to each other.
Edit: I tired the way Mike suggested but i still got the index out of range. What am I missing?
bool sumSame;
int sum3=0;
int sum4 = 0;
for (int i = 0; i < arr.GetLength(0); i++)
{
sum3 += arr[0, i];
}
for (int i = 0; i < arr.GetLength(0); i++)
{
sum4 = 0;
for (int j = 0; j < arr.GetLength(1); i++)
{
**sum4 += arr[i, j];**//The Error is Here
}
if (sum4 != sum3)
{
sumSame = false;
break;
}
}
sumSame = true
You would like to know if all rows in a 2D array have the same sum.
So, you need to write a function which computes the sum of a row.
Then your problem becomes one-dimensional: check whether a function invoked for every element of a one-dimensional array returns the same value for each element. (The fact that an element is in turn another array is irrelevant.)
If you do not want to (or do not know how to) write a function, then you can write the code which computes the sum of a row as a nested loop, (as you already tried to do,) but still, it helps if you conceptually treat these two tasks as completely different from each other, meaning that they should not mix their variables, and the outer loop should only use the result of the calculation of the inner loop.
Generally, the way we make sure that all elements of an array are equal to a certain value is that we compute the value of the first element, (at index 0,) and then we loop for each subsequent element (for( int i = 1; ...) and check whether the value computed for this element is equal to the value that we got for the first element.
You can add the sum of each array to the List<int> and check the number of distinct results with Distinct().Count(), if it's 1 the results are the same for all 2D array.
int[,] arr = new int[,]
{
{1,2,3 },
{3,2,1 },
{2,3,1 }
};
List<int> sums = new List<int>();
for (int i = 0; i < arr.GetLength(0); i++)
{
int sum = 0;
for (int j = 0; j < arr.GetLength(1); j++)
{
sum += arr[i, j];
}
sums.Add(sum);
}
bool sameResults = sums.Distinct().Count() == 1;

Calculating Combinations for a 7 digit binary number

I am trying to calculate all the Combinations of a 7 digit number. Each digit can occupy basically two values that's why I am calling it a binary number.
The digit are represented by FNMSDPL. Basically I want all the combinations of values and their sum.
I wrote the below code but its not working.
F[0] = 9.29;
F[1] = -4.47;
N[0] = 9.64;
N[1] = -5.77;
M[0]= -7.48;
M[1] = -2.13;
S[0] = 25.85;
S[1]= -3.55;
D[0]= 12.14;
D[1] = -4.90;
P[0] = 8.65;
P[1]= -0.85;
L[0] = 9.14;
L[1]= -1.73;
for (int i = 0; i < 2; i++)
{
for (int j = 0; j < 2; j++)
{
for (int k = 0; k < 2; k++)
{
for (int l = 0; l < 2; k++)
{
for (int m = 0; m < 2; m++)
{
for (int n = 0; n < 2; n++)
{
for (int o = 0; 0 < 2; o++)
{
double count = F[i] + M[j] + L[k] + S[l] + D[m] + P[n] + L[o];
System.Console.WriteLine(count);
}
}
}
}
}
}
}
Error Message:
Index was outside the bounds of the array.
I am getting the above error at "double count =" line.
The font selection on Stack Overflow may have resolved this one
for (int o = 0; 0 < 2; o++)
The condition should be using o instead of 0. (Tip: avoid using o or O as variable names.)
Edit: Another problem here (should be incrementing l, not k):
for (int l = 0; l < 2; k++)
I guess this won't work as expected:
for (int l = 0; l < 2; k++)
You should probably use something more clever than 7 nested for loops (since, as the other answers point out, this is terribly prone to error, especially when you have to make up 14 variable names). A recursive solution would do nicely here.
As for the sum, you don't need to generate all possibilities to know the sum of all 128 possible numbers. Observe that each binary digit (0 or 1) occurs exactly 64 times in each slot, so the sum total is just 64 times the sum of the 14 floats in your arrays.

Categories

Resources