Problems with displaying information from an array - c#

I am trying to make a simple program in C# code (Console Application), which prompts the user to enter 10 names and then the 10 names displayed at the end in a random order (not the order the names were entered in)
This is how far I have gotten:-
static void Main(string[] args)
{
string[] names = new string [10];
int i;
for ( i = 0; i < 10 ; i++)
{
Console.WriteLine("Give me name " + (i+1) );
names[i] = Console.ReadLine();
}
for (int j = 0; j <= 10; j++)
{
Console.WriteLine(names[j]);
}
Console.ReadLine();
}
So far I have been able to prompt the user for 10 names, and store those 10 names, and display them at the end, however, once they are displayed I get the error :- "IndexOutOfRangeException was unhandled" and the Console.WriteLine(names[j]); gets highlighted.
Lastly, once these problems are sorted, how do I display the names entered back in random order?
Thanks for reading.

You get from 0 to 9 from input, but try to print from 0 to 10.
The 10th item does not exist in the array.
Correct it like below:
for (int j = 0; j < 10; j++)
{
Console.WriteLine(names[j]);
}
Hope this helps.

The first loop runs from 0 to 9, but the second runs from 0 to 10, so you try to display an item that doesn't exist in the array. Change j <= 10 to j < 10 in the loop (just like in the first loop) to loop to 9 instead of 10.
Better yet, you can use i < names.Length and j < names.Length in the loops. That way you can change the size of the array and the loops will still work without any change.
To display the items in random order you would want to shuffle the array. The best method for that is a Fisher-Yates shuffle. Shuffle the items in the array like this:
Random rnd = new Random();
for (int i = 0; i < names.Length − 1; i++) {
int j = rnd.Next(i, names.Length);
string tmp = names[i];
names[i] = names[j];
names[j] = tmp;
}
Then you can just show the items from the array the way that you do now (with the correction in the loop).

To resolve error, only check for less than 10 (<10) instead of less than or equal to 10 (<=10)
and to get random order use Random class. Make sure only one random instance is created and you call Next so that new random number is generated in tight loop
Random random = new Random();
for (int j = 0; j < 10; j++)
{
int randomNumber = random.Next(1,10);
Console.WriteLine(names[randomNumber-1]);
}

The problem is that your index is 0 based, and contains 10 entries, but the last one is Array[9] not Array[10]
{Frank,Paul,John}
So Array[0] is Frank,
and Array[3] is... out of range.
Your loop uses
for (int j = 0; j <= 10; j++)
{
Console.WriteLine(names[j]);
}
The first time through, j = 0, names[j] would be Frank for us. Your problem is since 10 <= 10 is indeed true, it is looking for j[10], which doesn't exist.
The solution is to change j < 10
for (int j = 0; j < 10; j++)
{
Console.WriteLine(names[j]);
}

Related

How can i write which element corresponds to which score in 2 different arrays?

I have got 25 elements in my txt file. My code calculates their scores according to answer key. Then i would like to sort them without using sort.Array etc. I made it and a assigned them another array which is name is result. Now i would like to write the elements number according to order of result array
. For example the element 101' score 78. The element 105' s score is 25.
The result array sort them: 78-25
i would like to sort them : 101-105
my code is:
//arranging results according to their values
int temp = 0;
int[] elm = new int[result.Length];
for (int i = 0; i <= result.Length-1 ; i++)
{
for (int j = i+1 ; j < result.Length; j++)
{
if (result[i] < result[j])
{
temp = result[i];
result[i] = result[j];
result[j] = temp;
}
elm[j] = Convert.ToInt16(row[i,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;

IndexOutOfRangeException 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.

Categories

Resources