Skip to content

Commit

Permalink
40ms -> 23ms, by inlining the neighbour calculation, also fixed the t…
Browse files Browse the repository at this point in the history
…est suite
  • Loading branch information
Jumbub committed Sep 30, 2021
1 parent 987fb57 commit f64f4ad
Show file tree
Hide file tree
Showing 6 changed files with 259 additions and 193 deletions.
8 changes: 8 additions & 0 deletions readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,14 @@ Requires:

- https://www.libsdl.org/

### Running the tests

`make test`

Requires:

- https://github.com/catchorg/Catch2

### Running a benchmark

`make benchmark`
Expand Down
4 changes: 2 additions & 2 deletions results/benchmark.txt
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
----------------------------------------------------------------------------
Benchmark Time CPU Iterations
----------------------------------------------------------------------------
BM_NextBoard/min_time:5.000 38.6 ms 38.5 ms 181
BM_RenderNextBoard/min_time:5.000 40.7 ms 40.7 ms 171
BM_NextBoard/min_time:5.000 23.1 ms 23.1 ms 301
BM_RenderNextBoard/min_time:5.000 25.3 ms 25.2 ms 275
8 changes: 4 additions & 4 deletions src/board/generate.cpp
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
#include "generate.h"
#include "breeder.h"
#include <filesystem>
#include <memory>
#include <random>
#include <stdexcept>
#include <memory>
#include <tuple>

Board randomBoard(int width, int height) {
auto board = std::shared_ptr<bool[]>(new bool[width*height]);
for (int i = 0; i < height*width; ++i)
auto board = std::shared_ptr<bool[]>(new bool[width * height]);
for (int i = 0; i < height * width; ++i)
board[i] = rand() % 2;
return {board, width, height};
}
Expand All @@ -25,7 +25,7 @@ Board benchmarkBoard(int width, int height) {
"Did not meet minimum height required for the benchmark board");

srand(0);
auto board = std::shared_ptr<bool[]>(new bool[width*height]);
auto board = std::shared_ptr<bool[]>(new bool[width * height]);
for (int y = 0; y < height; ++y) {
for (int x = 0; x < width; ++x) {
const int i = y * width + x;
Expand Down
3 changes: 3 additions & 0 deletions src/board/generate.h
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
#pragma once

#include "board.h"
#include <vector>

Board randomBoard(int width, int height);

Board benchmarkBoard(int width, int height);

Board fromVector(std::vector<std::vector<bool>> board);
50 changes: 19 additions & 31 deletions src/board/next.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,28 +6,6 @@
#include <tuple>
#include <vector>

const NeighbourPositions getNeighbourPositions(const int px, const int py,
const int width,
const int height) {
NeighbourPositions positions = {};
int i = 0;
for (int y = -1; y <= 1; y++)
for (int x = -1; x <= 1; x++) {
if (y == 0 && x == 0)
continue;

auto xx = (px + x) % width;
if (xx < 0)
xx = xx + width;
auto yy = (py + y) % height;
if (yy < 0)
yy = yy + height;

positions[i++] = yy * width + xx;
}
return positions;
}

Board nextBoard(Board board) {
const auto &[input, width, height] = board;
if (height == 0)
Expand All @@ -43,17 +21,27 @@ Board nextBoard(Board board) {

auto alive = input[i];

auto neighboursPositions = getNeighbourPositions(x, y, width, height);
int neighboursCount = 0;
for (int n = 0; n < 8; n++) {
if (input[neighboursPositions[n]])
neighboursCount++;

// Optimisation (exit early if we know it's a dead cell)
if (neighboursCount > 3) {
break;
for (int y2 = -1; y2 <= 1; y2++)
for (int x2 = -1; x2 <= 1; x2++) {
if (y2 == 0 && x2 == 0)
continue;

auto xx = (x2 + x) % width;
if (xx < 0)
xx = xx + width;
auto yy = (y2 + y) % height;
if (yy < 0)
yy = yy + height;

if (input[yy * width + xx])
neighboursCount++;

// Optimisation (exit early if we know it's a dead cell)
if (neighboursCount > 3) {
break;
}
}
}

if (alive && (neighboursCount < 2 || neighboursCount > 3))
output[i] = false;
Expand Down
Loading

0 comments on commit f64f4ad

Please sign in to comment.