I have a program that should read in an integer value x from the console, and then print out a multi dimensional. The value of the row i on column j should be i *j. For example: if I input 3, the matrix should look like this:
1 2 3
2 4 6
3 6 9
Now, I have written this code in my Main function:
Console.WriteLine("Input a value: ");
int x = int.Parse(Console.ReadLine());
int[,] arr = new int[x,x];
for (int i = 0; i < x; i--)
{
for (int j = 0; j < x; j++)
{
arr[i, j] = arr[i, j] + arr[i, j];
Console.Write(arr[i, j] + " ");
}
}
Console.ReadLine();
So, when I input 3 from my code, I get the output:
0 0 0
What am I doing wrong here?
You have to change i-- to i++.
Put Console.WriteLine() after inner for loop. It will print a line break after every x numbers to make it loop like matrix.
You're saying The value of the row i on column j should be i *j, but I can't see any i * j in your code. Change your calculations to that: arr[i, j] = i * j;.
That should be it, but because your loops run from 0 to x - 1 and you want result to be as if it was from 1 to x you have to adapt your calculations and make it arr[i, j] = (i + 1) * (j + 1);.
Complete code should be:
Console.WriteLine("Input a value: ");
int x = int.Parse(Console.ReadLine());
int[,] arr = new int[x, x];
for (int i = 0; i < x; i++)
{
for (int j = 0; j < x; j++)
{
arr[i, j] = (i + 1) * (j + 1);
Console.Write(arr[i, j] + " ");
}
Console.WriteLine();
}
Console.ReadLine();
You´re saing that the value of arr[i, j] must be equals to i * j, but you´re not doing it on your code.
change
arr[i, j] = arr[i, j] + arr[i, j];
to
arr[i, j] = (i+1) * (j+1);
another thing that you need to change is that i are being decremented on the for loop, because of this code: i--. change it to i++
Seeing how the int[,] is full of zero's all your doing is adding zero + zero.
Seems like what you really want is this:
int[,] arr = new int[x,x];
for (int i = 0; i < x; i++)
{
for (int j = 0; j < x; j++)
{
arr[i, j] = (i+1) * (j + 1);
Console.Write(arr[i, j] + " ");
}
Console.Write("\r\n");
}
Console.ReadLine();
Related
I don't know what to do, my program is not working
I need to sort a two-dimensional array by the first elements of a row in descending order by rearranging the rows
(need to sort string without sort item)
Let's say I'm given an array:
1 2 3
4 5 6
7 8 9
As a result of the program, I need to get:
7 8 9
4 5 6
1 2 3
`
using System;
namespace BubbleSort
{
internal class Program
{
static void Main(string[] args)
{
//Объявление массива и его размерности
const int n = 3;
int bubble;
int[,] A =
{
{ 1, 2, 3 },
{ 4, 5, 6 },
{ 7, 8, 9 },
};
//Алгоритм пузырьковой сортировки
for (int i = 0; i < n; i++)
{
for(int j = 0; j < n - 1; j++)
{
if (A[i, 0] < A[i++, 0])
{
for(j = 0; j < n-1; j++)
{
bubble = A[i, j];
A[i, j] = A[i, j+1];
A[i, j+1] = bubble;
}
}
}
}
//Вывод массива
for (int y = 0; y < n; y++)
{
for (int x = 0; x < n; x++)
{
Console.Write(A[y, x] + " ");
}
Console.WriteLine();
}
}
}
}
`
From the code in your comments, I'm not sure why you have a nested loop for swapping the values since a single loop will do. I've removed that here.
If you refer to the pseudocode implementation on Wikipedia, you'll see that you need to keep running multiple passes across the array until everything is sorted. You can do this like so:
bool swapped;
do
{
swapped = false; // reset swapped
for (int i = 0; i < n - 1; i++) // loop through all but the last row
{
if (A[i, 0] < A[i + 1, 0]) // determine if this row needs to be swapped with the next row
{
swapped = true; // mark swapped
for (int j = 0; j < n; j++) // swap each item in row i with each item in row i+1
{
int tmp = A[i, j];
A[i, j] = A[i + 1, j];
A[i + 1, j] = tmp;
}
}
}
}
while (swapped); // if we swapped anything, we need to make another pass to ensure the array is sorted
We can also do away with the need for n by using .GetUpperBound(dimension) which returns a value between 0 and n - 1 (where n is the count of items in the array in that dimension). Because the result is effectively n - 1, I've modified the loop conditions slightly:
bool swapped;
do
{
swapped = false;
for (int i = 0; i < A.GetUpperBound(0); i++)
{
if (A[i, 0] < A[i + 1, 0])
{
swapped = true;
for (int j = 0; j <= A.GetUpperBound(1); j++)
{
int tmp = A[i, j];
A[i, j] = A[i + 1, j];
A[i + 1, j] = tmp;
}
}
}
}
while (swapped);
We can also refer to the "Optimizing bubble sort" section of the Wikipedia page and implement that instead, which will make our code run more optimally:
int n = A.GetUpperBound(0); // get the initial value of n
do
{
int newn = 0; // default newn to 0, so if no items are visited, it will remain 0 and the loop will exit
for (int i = 0; i < n; i++)
{
if (A[i, 0] < A[i + 1, 0])
{
for (int j = 0; j <= A.GetUpperBound(1); j++)
{
int tmp = A[i, j];
A[i, j] = A[i + 1, j];
A[i + 1, j] = tmp;
}
newn = i; // store the current (highest) value of i swapped
}
}
n = newn; // set the value of n to the highest value of i swapped
}
while (n > 0); // loop until n == 0
The logic here (as explained on Wikipedia) is that by the end of the first pass, the last item is in the correct position. By the end of the second pass, the second-to-last and last items are in the correct position, and so on. So each time, we can visit one less item. When we have 0 items to visit, we have 0 items to swap, and the sort is complete.
You can see this optimised version in this YouTube visualisation.
I think the line
if (A[i, 0] < A[i++, 0])
should read
if (A[i, 0] < A[i+ 1, 0])
So far I have,
int[,] array2d = new int[20, 20];
for (int i = 1; i < array2d.GetLength(0); i++)
{
for (int j = 1; j < array2d.GetLength(1); j++)
{
array2d[i, j] = i * j ;
Console.WriteLine(array2d[i, j]);
}
}
but this is skipping some quite a few numbers, I tried to fix it by checking if I is <= but that throws a IndexOutOfRangeException
Is there some point where I made a major error? or is it a simple one.
Arrays are zero-based by default; so your array is [0..19, 0..19]; however, you want a different range: [1..20, 1..20]. We should not mix them: either (better choice)
int[,] array2d = new int[20, 20];
// i, j - array indexes
for (int i = 0; i < array2d.GetLength(0); i++)
{
for (int j = 0; j < array2d.GetLength(1); j++)
{
// since i, j are array indexes we multiply (i + 1) * (j + 1)
array2d[i, j] = (i + 1) * (j + 1);
Console.Write($"{array2d[i, j],3} ");
}
Console.WriteLine();
}
Or
int[,] array2d = new int[20, 20];
// i, j are values to be multiplied
for (int i = 1; i <= array2d.GetLength(0); i++)
{
for (int j = 1; j <= array2d.GetLength(1); j++)
{
// since i, j are values we have to compute array's indexes: i - 1, j - 1
array2d[i - 1, j - 1] = i * j;
Console.Write($"{array2d[i - 1, j - 1],3} ");
}
Console.WriteLine();
}
int[,] array2d = new int[20, 20];
for (int i = 0; i < 20; i++)
{
for (int j = 0; j < 20; j++)
{
array2d[i, j] = (i+1) * (j+1) ;
Console.WriteLine(array2d[i, j]);
}
}
Your problem was that when you define array like new int[20] then it can be iterated from 0 to 19, when you try to acces its value at index 20 you get this exception because index 20 doesnt exist in this array.
When you call arrays .GetLength method it returns its count of fields which is 20, not its maximum index which is 19.
I am trying to solve LU decomposition with the Doolittle Algorithm – according to this document. Without parallelization, code works fine. However, I would like to make this code run in parallel - trying to make a parallel outer and two inner loops. Unfortunately I am still missing something. If I tried to first make the outer loop run in parallel, I received a bad result.
I tried to detect where there might be a collision. I locked those places afterwards, but I still did not receive the right result. I added them to the copied code as comments. What am I doing wrong, do I need lock out other places?
What´s the right implementation of outer loop?
How would inner loops look like?
Thank you in advance.
Implementation of algorithm (sequential)
//upper triangle
var upper = new double[arr.GetLength(0), arr.GetLength(0)];
//lower triangle
var lower = new double[arr.GetLength(0), arr.GetLength(0)];
//field initialization
for (int i = 0; i < n; i++)
{
for (int j = i; j < n; j++)
upper[i, j] = arr[i, j];
for (int j = i + 1; j < n; j++)
lower[j, i] = arr[j, i];
lower[i, i] = 1;
}
for(int i=0; i<n; i++)
{
for (int j = i; j < n; j++)
{
for (int k = 0; k < i; k++)
{
upper[i, j] = upper[i, j] - (lower[i, k] * upper[k, j]);
}
}
for (int j = i + 1; j < n; j++)
{
for (int k = 0; k < i; k++)
{
lower[j, i] = lower[j, i] - (lower[j, k] * upper[k, i]);
}
lower[j, i] = lower[j, i] / upper[i, i];
}
}
Implementation of algorithm (parallel)
//upper triangle
var upper = new double[arr.GetLength(0), arr.GetLength(0)];
//lower triangle
var lower = new double[arr.GetLength(0), arr.GetLength(0)];
//field initialization
for (int i = 0; i < n; i++)
{
for (int j = i; j < n; j++)
upper[i, j] = arr[i, j];
for (int j = i + 1; j < n; j++)
lower[j, i] = arr[j, i];
lower[i, i] = 1;
}
//making outer loop parallel
Parallel.For(0, n, (i, state) =>
{
//possibly make this loop parallel also
for (int j = i; j < n; j++)
{
for (int k = 0; k < i; k++)
{
//lower[i,k] is it potential problem?
/*
* I tried this solution
* double a;
* lock(lowerLock){
* a = lower[i,k];
* }
* upper[i, j] = upper[i, j] - (a * upper[k, j])
*/
upper[i, j] = upper[i, j] - (lower[i, k] * upper[k, j]);
}
}
//possibly make this loop parallel also
for (int j = i + 1; j < n; j++)
{
for (int k = 0; k < i; k++)
{
//upper [k,i] is it potential problem?
/*
* I tried this solution
* double b;
* lock(upperLock){
* b = upper[k, i];
* }
* lower[j, i] = lower[j, i] - (lower[j, k] * b);
*/
lower[j, i] = lower[j, i] - (lower[j, k] * upper[k, i]);
}
lower[j, i] = lower[j, i] / upper[i, i];
}
});
sequential right result
Concatenation Upper triangle Lower triangle
2 -1 -2 2 -1 -2 1 0 0
-2 4 -1 0 4 -1 -2 1 0
-2 -1 3 0 0 3 -2 -1 1
parallel bad result
Concatenation Upper triangle Lower triangle
2 -1 -2 2 -1 -2 1 0 0
-2 4 -1 0 4 -1 -2 1 0
-2 -1 3 0 0 10 -->BAD -2 -1 1
EDIT
I tried to lock all the approaches to the fields with one lock. I am aware of loosing all parallelization in this way. However, I wanted to achieve at least the right result, unfortunately without success.
static object mylock = new object();
//making outer loop parallel
Parallel.For(0, n, (i, state) =>
{
for (int j = i; j < n; j++)
{
for (int k = 0; k < i; k++)
{
lock (mylock)
{
upper[i, j] = upper[i, j] - (lower[i, k] * upper[k, j]);
}
}
}
for (int j = i + 1; j < n; j++)
{
for (int k = 0; k < i; k++)
{
lock (mylock)
{
lower[j, i] = lower[j, i] - (lower[j, k] * upper[k, i]);
}
}
lock (mylock)
{
lower[j, i] = lower[j, i] / upper[i, i];
}
}
});
The parallel loops write to the same array, right?
upper[i, j] = upper[i, j] - (lower[i, k] * upper[k, j]);
But it is not defined, when which loop will write to a position in your array. So two loops will NOT write to the same index but read from an index, where the other loop might have already written to.
You can't parallize your algorithm this way.
Hi my problem is I can't get the numbers with more than 2 digits from this matrix if anyone can help I would appriciate it here i my code :
Console.Write("x: ");
int x = int.Parse(Console.ReadLine());
Console.Write("y: ");
int y = int.Parse(Console.ReadLine());
int[,] arr = new int[x, y];
int[,] arr2 = new int[x, y];
Random rand = new Random();
for (int i = 0; i < arr.GetLength(0); i++)
{
for (int j = 0; j < arr.GetLength(1); j++)
{
int randNUm = rand.Next(0, 20);
arr[i, j] = randNUm;
Console.Write(arr[i, j] + " ");
if (arr[i, j] >= 10)
{
arr2[i,j] = arr[i,j]
}
}
}
Actually you have done your job, all it remains is to display the results. If
the task specifies that the printing must be done in 2 steps as you imply,
try:
for (int i = 0; i < arr.GetLength(0); i++)
{
for (int j = 0; j < arr.GetLength(1); j++)
{
int randNUm = rand.Next(0, 20);
arr[i, j] = randNUm;
Console.Write(arr[i, j] + " ");
if (arr[i, j] >= 10)
{
arr2[i,j] = arr[i,j]
}
}
}
Console.WriteLine("---Proceeding to 2 digit numbers---");
for (int i = 0; i < arr2.GetLength(0); i++)
{
for (int j = 0; j < arr2.GetLength(1); j++)
{
Console.Write(arr2[i, j] + " ");
}
}
EDIT : Consider what Henk comments and try to optimise your solution.
I am trying to create a matrix of Random numbers using Polar Rejection method with the code below. I don't see any error but the console does not show any results. My code is below:
class Program
{
static void Main(string[] args)
{
Program.GenerateRandom();
}
public static void GenerateRandom()
{
Console.WriteLine("Please enter newtrials.");
int newTrials=Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Please enter Steps.");
int newSteps = Convert.ToInt32(Console.ReadLine());
int i = 0;
int j = 0;
double[,] v = new double[newTrials,newSteps];
double[,] d = new double[newTrials, newSteps];
double[,] l = new double[newTrials, newSteps];
double[,] Z = new double[newTrials, newSteps];
for (i = 0; i < newTrials; ++j)
{
for (j = 0; j < newSteps; ++i)
{
do
{
Random rnd = new Random();
v[i, j] = 2 * rnd.NextDouble() - 1;
d[i, j] = 2 * rnd.NextDouble() - 1; ;
l[i, j] = Math.Pow(v[i, j], 2) + Math.Pow(d[i, j], 2);
}
while (l[i, j] >= 1.0);
}
Z[i, j] = Math.Sqrt(-2 * Math.Log(l[i, j]) / l[i, j]) * v[i, j];
}
Console.WriteLine("values are:{0},{1}",Z[0,0],Z[0,1]);
Console.ReadLine();
}
}
}
I see two things that are I believe are errors in this code:
for (i = 0; i < newTrials; ++j) and for (j = 0; j < newSteps; ++i). You're incrementing the counter for the j loop in i and the counter for i loop in j. This is causing a "System.IndexOutOfRangeException" when I run your code because the j loop isn't getting incremented in the j loop and thus the loop isn't stopping.
Z[i, j] = Math.Sqrt(-2 * Math.Log(l[i, j]) / l[i, j]) * v[i, j]; at this point in the program's execution the loops have reached the bounds of the arrays you declared above. So if the user input 10 and 10 this code is calling Z[10, 10]. Since arrays are zero based Z only has upper bounds of Z[9,9] this is throwing a "System.IndexOutOfRangeException" as well.
The other consequence of the 2nd issue is that you're only writing an answer to the last index of the second dimension of the Z array. Meaning, if we use our 10 and 10 example again, results will only be written to Z[0, 9], Z[1, 9], Z[2, 9], Z[3, 9], Z[4, 9], Z[5, 9], Z[6, 9], Z[7, 9], Z[8, 9], and Z[9, 9]. I'm not sure what you're intending to do with this code but I think you have some logic errors.
I think you want something like the following:
Console.WriteLine("Please enter newtrials.");
int newTrials = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Please enter Steps.");
int newSteps = Convert.ToInt32(Console.ReadLine());
int i = 0;
int j = 0;
double[,] v = new double[newTrials, newSteps];
double[,] d = new double[newTrials, newSteps];
double[,] l = new double[newTrials, newSteps];
double[,] Z = new double[newTrials, newSteps];
Random rnd = new Random();
for (i = 0; i < newTrials; i++)
{
for (j = 0; j < newSteps; j++)
{
do
{
v[i, j] = 2.0 * rnd.NextDouble() - 1.0;
d[i, j] = 2.0 * rnd.NextDouble() - 1.0;
l[i, j] = Math.Pow(v[i, j], 2.0) + Math.Pow(d[i, j], 2.0);
}
while (l[i, j] >= 1.0);
Z[i, j] = Math.Sqrt(-2 * Math.Log(l[i, j]) / l[i, j]) * v[i, j];
}
}
for (i = 0; i < newTrials; i++)
{
Console.Write("[");
for (j = 0; j < newSteps; j++)
{
Console.Write("{0}, ", Z[i, j]);
}
Console.Write("]\n");
}
Console.ReadLine();