Is there any way to speed up array initialization? - c#

I have a function that stores values inside some arrays. Every time the function is called, the arrays have to be cleared before putting items in them.
public static void UpdateAttackedPieces()
{
attackedSquares = new List<int>[2][];
for (int color = 0; color < 2; color++) attackedSquares[color] = new List<int>[64];
for (int color = 0; color < 2; color++) for (int i = 0; i < 64; i++) attackedSquares[color][i] = new List<int>();
checkAttackersRays = new List<int>[2][];
for (int color = 0; color < 2; color++) checkAttackersRays[color] = new List<int>[64];
for (int color = 0; color < 2; color++) for (int i = 0; i < 64; i++) checkAttackersRays[color][i] = new List<int>();
// Update arrays
}
(It is a chess program and the function is for updating pieces under attack).
attackedSquares is an array (one per color) of the 64 squares on the board which holds information about its attackers (so attackedSquares[0][4][2] is the third attacker on the fifth square for white, for example)
I've done some testing and about 35% of the time it takes to run the function is spent initializing the jagged arrays. Is there a faster way to do this?

Thanks to #Matthey Watson's comment, I was able to bring the time down from 6.5 seconds to less than 1 second with this change in the code:
public static void UpdateAttackedPieces()
{
for (int color = 0; color < 2; color++) for (int i = 0; i < 64; i++) attackedSquares[color][i].Clear();
for (int color = 0; color < 2; color++) for (int i = 0; i < 64; i++) checkAttackersRays[color][i].Clear();
// Update arrays
}

Related

Is it possible to add new Rectangle variable with for loop in winform c#?

Is it possible to make new rectangle variable with one for loop ? or should i declare it one by one ?
I try to make snake and ladder map and it will be much easier if i can declare 100 rectangle with only one for loop.
I tried to make the code but it's not working.
for (int i = 0; i < 100; i++)
{
Rectangle String.Format("Land {}", i) = new Rectangle(0, 0, 200, 100);
}
You probably want an array:
var rectangles = new Rectangle[100];
for (int i = 0; i < 100; i++)
{
rectangles[i] = new Rectangle(0, 0, 200, 100);
}
An array can hold many objects and you have only one name + a number to access it.
For a square, you can do something like
var rectangles = new Rectangle[100];
for (int i = 0; i < 10; i++)
{
for (int j = 0; j < 10; j++)
{
rectangles[i*10 + j] = new Rectangle(i*100, j*100, 100, 100);
}
}
Even cooler, there's a 2D version of an array:
var rectangles = new Rectangle[10,10];
for (int i = 0; i < 10; i++)
{
for (int j = 0; j < 10; j++)
{
rectangles[i, j] = new Rectangle(i*100, j*100, 100, 100);
}
}
Don't forget to add the rectangles to your Form in order to display it.
When you understood the concept of an array, you might want to have a look at Lists and then Dictionaries. They are more flexible, because they don't have a fixed size.

2 dimensional array with multiple values for each x and y

I am looking to create a 2-dimensional array that remaps a texture. So for each pixel it will store a hsv value so that it can be recreated programmatically. (In C# preferrably)
My question is is there an algorithm/code (Linq/ArrayList etc) that would enlarge the resulting array and therefore image - ie: by a factor of ten for example.
Current code for recreating 1 to 1 (this is the loop):
imageHueArray = new float[width,height];
for (int i = 0; i < img.width; i++)
{
for (int j = 0; j < img.height; j++)
{
imageHueArray[i,j] = pixelH;
}
}
New edit:
I have attempted new code based on some suggestions and links I looked at - I think it is getting closer, but not there yet (any better suggestions appreciated).
I replaced j with z in the array when loops through i in outer loop (as outside j loop).
This code increases size of image, but the increase portion is only blank (or at least using a fixed pixel, 0,0 perhaps) - I think it is in issue with the i/x plane as this does not seem to loop correctly, although the code looks okay (to me).
for (var i = 0; i < newRows; i++) {
for (var j = 0; j < newCols; j++) {
for (var k = 0; k < resizeScale; k++) {
imageHueArray[i,j] = pixelHSV;
}
z=j;
}
for (var k = 0; k < resizeScale; k++) {
imageHueArray[i,z] = pixelHSV;
}
}

Subarrays from a 2D multdimensional array

I've run into a stall trying to put together some code to average out 10x10 subarrays of a 2D multidimensional array.
Given a multidimensional array
var myArray = new byte[100, 100];
How should I go about creating 100 subarrays of 100 bytes (10x10) each.
Here are some examples of the value indexes the subarrays from the multidimensional would contain.
[x1,y1,x2,y2]
Subarray1[0,0][9,9]
Subarray2[10,10][19,19]
Subarray3[20,20][29,29]
Given these subarrays, I would then need to average the subarray values to create a byte[10,10] from the original byte[100,100].
I realize this is not unbelievably difficult, but after spending 4 days debugging very low-level code and now getting stuck on this would appreciate some fresh eyes.
Use this as a reference. I used ints just for ease of use. Code is untested. but the idea is there.
var rowSize = 100;
var colSize = 100;
var arr = new int[rowSize, colSize];
var r = new Random();
for (int i = 0; i < rowSize; i++)
for (int j = 0; j < colSize; j++)
arr[i, j] = r.Next(20);
for (var subcol = 0; subcol < colSize / 10; subcol++)
{
for (var subrow = 0; subrow < colSize/10; subrow++)
{
var startX = subcol*10;
var startY = subrow*10;
var avg = 0;
for (var x=0; x<10; x++)
for (var y = 0; y < 10; y++)
avg += arr[startX + x, startY + y];
avg /= 10*10;
Console.WriteLine(avg);
}
}
It looks like you're new to SO. Next time try to post your attempt at the problem; it's better to fix your code.
The only challenge is figuring out the function, that given the subarray index we're trying to populate, would give you the correct row and column indexes in your original 100x100 array; the rest would just be a matter of copying the values:
// psuedocode
// given a subarrayIndex of 0 to 99, these will calculate the correct indices
rowIndexIn100x100Array = (subarrayIndex / 10) * 10 + subArrayRowIndexToPopulate;
colIndexIn100x100Array = (subarrayIndex % 10) * 10 + subArrayColIndexToPopulate;
I'll leave it as an exercise to you to deduce why the above functions correctly calculate the indices.
With the above, we can easily map the values:
var subArrays = new List<byte[,]>();
for (int subarrayIndex = 0; subarrayIndex < 100; subarrayIndex++)
{
var subarray = new byte[10, 10];
for (int i = 0; i < 10; i++)
for (int j = 0; j < 10; j++)
{
int rowIndexIn100x100Array = (subarrayIndex / 10) * 10 + i;
int colIndexIn100x100Array = (subarrayIndex % 10) * 10 + j;
subarray[i, j] = originalArray[rowIndexIn100x100Array, colIndexIn100x100Array];
}
subArrays.Add(subarray);
}
Once we have the 10x10 arrays, calculating the average would be trivial using LINQ:
var averages = new byte[10, 10];
for (int i = 0; i < 10; i++)
for (int j = 0; j < 10; j++)
{
averages[i, j] = (byte)subArrays[(i * 10) + j].Cast<byte>().Average(b => b);
}
Fiddle.

Filling matrix with for loops

Firstly, I fill the array with "0"s and then want to replace the first row with "1"s. Can not understand why the 2nd "for" loop fills the whole matrix with "1"s.
int i, j, array[length][width];
for (i = 0; i < length; i++) {
for (j = 0; j < width; j++) {
array[i][j] = 0;
}
}
for (i = 0; i < width; i++) {
array[0][i] = 1;
}`
I ran the code and it only filled the first row of the matrix with 1's. Try running it again.

Lack of Randomness in Map Generator

I am trying to generate random numbers 0-49. I want to draw the links in a grid as long as the random number is not 0. Every time I do get a 0, it is followed by another ten 0s (give or take). In my research, they said this would be the problem if I kept creating new instances of my Random, but I am not doing that. My code is as follows:
//Class begins
namespace Mascape
{
public class Game1 : Game
{
GraphicsDeviceManager graphics;
SpriteBatch spriteBatch;
Wall[, ,] walls = new Wall[2, 15, 10];
int mapWidth=15;
int mapHeight=10;
Random rand = new Random(); //Outside of any methods or loops.
int mapFullness;
//The following is in my Initialize() method
//i is horizontal vs. vertical link
//j is the x position of the link
//k is the y position of the link
mapFullness = 50;
for (int i = 0; i < 2; ++i)
{
for (int j = 0; j < mapWidth; ++j)
{
for (int k = 0; k < mapHeight; ++k)
{
if (!(rand.Next(50) == 0))
{
walls[i, j, k].active = true; //Links are drawn if active
}
}
}
}
I am trying to draw a grid with randomly missing links. The objective is to have them spread out, appearing about one in 50. This is the actual result:
Any idea why the randomness is lacking? Let me know if you would like more info, please.
There should be more to this. See the following code copied from yours generate random as expected.
Random rand = new Random();
int mapWidth = 5;
int mapHeight = 10;
for (int i = 0; i < 2; ++i)
{
for (int j = 0; j < mapWidth; ++j)
{
for (int k = 0; k < mapHeight; ++k)
{
Console.WriteLine(rand.Next(50));
}
}
}

Categories

Resources