Question About CPP-C#, Performance, and Square Represenation
Posted: Sat Sep 29, 2012 7:22 pm
Hi,
I decide to take a shot at a chess engine this past July. I used C# because it is what I am familiar with (I have not used C or CPP in a long time).
I am hooked
The engine works but after about 5 ply, it gets slow. All I use for searching is negamax with pruning - no Zobrist or iterative deepening.
My perft with a ply of 5 takes 90+ seconds. Compared to some other engines, I'm toast
My board's squares is an array of my piece object. Each piece object contains a list of moves and a few other variables. I generate moves for all pieces after a move is made. I feel this is where the latency appears and so I tried bitboards.
In the bitboards model, I did not get an increase in performance. I found that I still rely on my squares being an array of pieces and feel this might be why I did not get a performance increase. Working with OO makes it neat but I really feel all the new initializations of objects along with garbage collection might be causing the latency.
I read some posts here and and feel I found the answers I needed to read but I now need to understand
Here are my thoughts and maybe a question or two. I hope someone can review and provide me a nudge in the right direction.
1. C# should not be that much slower than CPP if I design the engines the same. If I am willing to relearn CPP and am patient, go for it.
2. I need to change my squares array to contain bytes representing a piece. With bitboards, I should only need to reference this array as a lookup to determine a capture occupancy.
3. I think I should generate moves into an array on the board and not a list per piece. The moves should just be for the moving side. I use the Mayothi move generation style but seem to be getting a grasp on the magics. Cutting over should help.
4. I have used DeBruijn to get square indexes from the bitboards. I need to use this only when I need to. This really should only be when generating moves as noted in #3.
I feel that following these I can move away from an object based design into a more static design. I'll get away from all the "new" objects, lists, and garbage collection and I believe I should see a drastic increase in performance.
Thank you in advance for any input and advice
-Cheney
I decide to take a shot at a chess engine this past July. I used C# because it is what I am familiar with (I have not used C or CPP in a long time).
I am hooked
The engine works but after about 5 ply, it gets slow. All I use for searching is negamax with pruning - no Zobrist or iterative deepening.
My perft with a ply of 5 takes 90+ seconds. Compared to some other engines, I'm toast
My board's squares is an array of my piece object. Each piece object contains a list of moves and a few other variables. I generate moves for all pieces after a move is made. I feel this is where the latency appears and so I tried bitboards.
In the bitboards model, I did not get an increase in performance. I found that I still rely on my squares being an array of pieces and feel this might be why I did not get a performance increase. Working with OO makes it neat but I really feel all the new initializations of objects along with garbage collection might be causing the latency.
I read some posts here and and feel I found the answers I needed to read but I now need to understand
Here are my thoughts and maybe a question or two. I hope someone can review and provide me a nudge in the right direction.
1. C# should not be that much slower than CPP if I design the engines the same. If I am willing to relearn CPP and am patient, go for it.
2. I need to change my squares array to contain bytes representing a piece. With bitboards, I should only need to reference this array as a lookup to determine a capture occupancy.
3. I think I should generate moves into an array on the board and not a list per piece. The moves should just be for the moving side. I use the Mayothi move generation style but seem to be getting a grasp on the magics. Cutting over should help.
4. I have used DeBruijn to get square indexes from the bitboards. I need to use this only when I need to. This really should only be when generating moves as noted in #3.
I feel that following these I can move away from an object based design into a more static design. I'll get away from all the "new" objects, lists, and garbage collection and I believe I should see a drastic increase in performance.
Thank you in advance for any input and advice
-Cheney