85 lines
2.5 KiB
C#
85 lines
2.5 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using GameOfLife.Entities;
|
|
|
|
namespace GameOfLife
|
|
{
|
|
public class LifeArray : LifeBase
|
|
{
|
|
protected bool[,] World;
|
|
private bool[,] _nextGeneration;
|
|
|
|
//private Task _processTask;
|
|
public int SizeX { get; private set; }
|
|
public int SizeY { get; private set; }
|
|
|
|
public override bool IsCellAlive(Cell cell)
|
|
{
|
|
return IsCellAlive(cell.Item1, cell.Item2);
|
|
}
|
|
|
|
public override bool IsCellAlive(short x, short y)
|
|
{
|
|
// first check boundaries
|
|
if (x < 0 || x >= SizeX || y < 0 || y >= SizeY)
|
|
return false;
|
|
return IsCellAlive_NoBoundaryCheck(x, y);
|
|
}
|
|
|
|
private bool IsCellAlive_NoBoundaryCheck(short x, short y) => World[x, y];
|
|
|
|
public LifeArray(Pattern pattern)
|
|
: this(pattern.GetBoundaryMax().Item1, pattern.GetBoundaryMax().Item2)
|
|
{
|
|
foreach (var cell in pattern)
|
|
{
|
|
ToggleCell(cell);
|
|
}
|
|
}
|
|
|
|
public LifeArray(Cell sizes) : this (sizes.Item1, sizes.Item2) { }
|
|
|
|
public LifeArray(short sizeX, short sizeY)
|
|
{
|
|
if (sizeX <= 0 || sizeY <= 0) throw new ArgumentOutOfRangeException("sizeX", "Size must be greater than zero");
|
|
SizeX = sizeX;
|
|
SizeY = sizeY;
|
|
World = new bool[sizeX, sizeY];
|
|
_nextGeneration = new bool[sizeX, sizeY];
|
|
}
|
|
|
|
protected override bool ToggleCell_Internal(Cell cell)
|
|
{
|
|
return World[cell.Item1, cell.Item2] = !World[cell.Item1, cell.Item2];
|
|
}
|
|
|
|
protected override int IncrementGeneration_Internal()
|
|
{
|
|
for (short x = 0; x < SizeX; x++)
|
|
for (short y = 0; y < SizeY; y++)
|
|
{
|
|
var shouldLive = ShouldLive(x, y);
|
|
_nextGeneration[x, y] = shouldLive;
|
|
}
|
|
|
|
// now flip the back buffer so we can start processing on the next generation
|
|
var flip = _nextGeneration;
|
|
_nextGeneration = World;
|
|
World = flip;
|
|
|
|
return Population;
|
|
}
|
|
|
|
public override IEnumerable<Cell> LivingCells
|
|
{
|
|
get
|
|
{
|
|
for (short y=0; y<SizeY;y++)
|
|
for (short x =0; x<SizeX;x++)
|
|
if (IsCellAlive_NoBoundaryCheck(x, y))
|
|
yield return new Cell(x, y);
|
|
}
|
|
}
|
|
}
|
|
}
|