Jump to page: 1 2
Thread overview
Conway's game of life
Feb 01, 2015
gedaiu
Feb 01, 2015
Tobias Pankrath
Feb 01, 2015
Foo
Feb 02, 2015
gedaiu
Feb 01, 2015
FG
Feb 02, 2015
gedaiu
Feb 02, 2015
FG
Feb 02, 2015
FG
Feb 02, 2015
gedaiu
Feb 02, 2015
data man
Feb 02, 2015
bearophile
Feb 03, 2015
Paul
Feb 03, 2015
Paul
Feb 03, 2015
bearophile
Feb 03, 2015
Paul
Feb 03, 2015
bearophile
February 01, 2015
Hi,

I implemented Conway's game of life in D. What do you think that
I can improve to this program to take advantage of more D
features?

https://github.com/gedaiu/Game-Of-Life-D

Thanks,
Bogdan
February 01, 2015
1. I prefer

alias CellList = Cell[];
over
alias Cell[] CellList;

2. Do you really need to create a complete new CellList for every single removal? If so, you'd know the size of the new list in advance and can allocate it directly at the correct size.

I get the impression that you think Cell[] is a linked list but it's an array slice.


February 01, 2015
On Sunday, 1 February 2015 at 21:00:07 UTC, gedaiu wrote:
> Hi,
>
> I implemented Conway's game of life in D. What do you think that
> I can improve to this program to take advantage of more D
> features?
>
> https://github.com/gedaiu/Game-Of-Life-D
>
> Thanks,
> Bogdan

For each remove you create a new array. That is lavish. You should use a bool inside the struct Cell. If it's false, the cell is not displayed and is out of the game.
My suggestion: don't use the D GC, it's crap. Try to circumvent the GC wherever possible. Therefore you should use the -vgc compiler flag and the @nogc attribute.
February 01, 2015
On 2015-02-01 at 22:00, gedaiu wrote:
> I implemented Conway's game of life in D.

I think you are playing a different game here.

    /// Count cell neighbours
    long neighbours(Cell myCell, CellList list) {
        long cnt;
        foreach(cell; list) {
            auto diff1 = abs(myCell.x - cell.x);
            auto diff2 = abs(myCell.y - cell.y);
            if(diff1 == 1 || diff2 == 1) cnt++;   // Why || instead of && ???
        }
        return cnt;
    }
February 02, 2015
On Sunday, 1 February 2015 at 21:00:07 UTC, gedaiu wrote:
> Hi,
>
> I implemented Conway's game of life in D. What do you think that
> I can improve to this program to take advantage of more D
> features?
>
> https://github.com/gedaiu/Game-Of-Life-D
>
> Thanks,
> Bogdan

If the subject of the game "Life" is interesting to you, look at these links:
http://en.wikipedia.org/wiki/Hashlife
http://golly.sourceforge.net
February 02, 2015
It's true that I have to change that function. Thanks for the notice!

Why do you think that D's GC is crap?




On Sunday, 1 February 2015 at 21:54:43 UTC, Foo wrote:
> On Sunday, 1 February 2015 at 21:00:07 UTC, gedaiu wrote:
>> Hi,
>>
>> I implemented Conway's game of life in D. What do you think that
>> I can improve to this program to take advantage of more D
>> features?
>>
>> https://github.com/gedaiu/Game-Of-Life-D
>>
>> Thanks,
>> Bogdan
>
> For each remove you create a new array. That is lavish. You should use a bool inside the struct Cell. If it's false, the cell is not displayed and is out of the game.
> My suggestion: don't use the D GC, it's crap. Try to circumvent the GC wherever possible. Therefore you should use the -vgc compiler flag and the @nogc attribute.

February 02, 2015
I don't think that the line of code is wrong. If use && the function will check for neighbours only on diagonals. Having || allows the search on the vertical and horizontal axis and diagonals.

There are some tests that check the function:

unittest {
	CellList world = [ Cell(0,0), Cell(0,1), Cell(0,2), Cell(1,0), Cell(1,2), Cell(2,0), Cell(2,1), Cell(2,2) ];
	assertEqual(Cell(1,1).neighbours(world), world.length);
}

unittest {
	CellList world = [ Cell(0,0), Cell(1,1), Cell(2,2), Cell(3,3) ];
	assertEqual(Cell(1,1).neighbours(world), 2);
}

I don't see a glitch.

Thanks,
Bogdan



On Sunday, 1 February 2015 at 22:51:42 UTC, FG wrote:
> On 2015-02-01 at 22:00, gedaiu wrote:
>> I implemented Conway's game of life in D.
>
> I think you are playing a different game here.
>
>     /// Count cell neighbours
>     long neighbours(Cell myCell, CellList list) {
>         long cnt;
>         foreach(cell; list) {
>             auto diff1 = abs(myCell.x - cell.x);
>             auto diff2 = abs(myCell.y - cell.y);
>             if(diff1 == 1 || diff2 == 1) cnt++;   // Why || instead of && ???
>         }
>         return cnt;
>     }

February 02, 2015
Bloody Thunderbird has sent a reply to the OP and not to the NG.

On 2015-02-02 at 11:45, gedaiu wrote:
> I don't think that the line of code is wrong. If use && the function will check for neighbours only on diagonals. Having || allows the search on the vertical and horizontal axis and diagonals.

In short: Yes, && alone would check only diagonals, but I forgot to tell you to also change the ==.

(diff1 == 1 || diff2 == 1) -- bad, accepts whole neighbouring rows and columns
(diff1 == 1 && diff2 == 1) -- bad, accepts only neighbouring diagonals
(diff1 <= 1 && diff2 <= 1) -- correct, I think :)

This unittest should show the difference:

unittest {
    CellList world = [ Cell(0,0), Cell(0,1), Cell(0,2), Cell(0,3) ];
    assertEqual(Cell(1,1).neighbours(world), 3);
}

Cell(0,3) is not a neighbour bit fits the (diff1 == 1 || diff2 == 1) criterion.
February 02, 2015
On 2015-02-02 at 12:23, FG wrote:
> Cell(0,3) is not a neighbour bit fits the (diff1 == 1 || diff2 == 1) criterion.

s/bit/but/
February 02, 2015
Uf...  you are right!

I've fixed it.

Thanks!


On Monday, 2 February 2015 at 11:23:17 UTC, FG wrote:
> Bloody Thunderbird has sent a reply to the OP and not to the NG.
>
> On 2015-02-02 at 11:45, gedaiu wrote:
>> I don't think that the line of code is wrong. If use && the function will check for neighbours only on diagonals. Having || allows the search on the vertical and horizontal axis and diagonals.
>
> In short: Yes, && alone would check only diagonals, but I forgot to tell you to also change the ==.
>
> (diff1 == 1 || diff2 == 1) -- bad, accepts whole neighbouring rows and columns
> (diff1 == 1 && diff2 == 1) -- bad, accepts only neighbouring diagonals
> (diff1 <= 1 && diff2 <= 1) -- correct, I think :)
>
> This unittest should show the difference:
>
> unittest {
>     CellList world = [ Cell(0,0), Cell(0,1), Cell(0,2), Cell(0,3) ];
>     assertEqual(Cell(1,1).neighbours(world), 3);
> }
>
> Cell(0,3) is not a neighbour bit fits the (diff1 == 1 || diff2 == 1) criterion.

« First   ‹ Prev
1 2