For my engine, I think I am doing something different from most engines, and I wonder if there are any drawbacks.
1) I use the transposition table to keep track of PV (the PV printing routine just follows the hash move at each position to get the PV).
That I think can only affect thinking output and not strength, so this is a minor issue.
2) I don't differentiate between root and non-root nodes. When it's the engine's turn to move, it just calls negamax on the root position, and then return the hash move from the transposition table when negamax returns (if not interrupted). My code is carefully written so that the "root" negamax call will always store a hash move in the TT. It also allows clean implementation of aspiration window. Unlike most (actually every I have seen) engines, it doesn't generate a list of legal moves, and call negamax on each resulting position.
It seems to work quite well for my engine, but does it have any negative impact that I didn't see?
3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
Not differentiating root and non-root / pondering approach
Moderator: Ras
-
- Posts: 12792
- Joined: Wed Mar 08, 2006 8:57 pm
- Location: Redmond, WA USA
Re: Not differentiating root and non-root / pondering approa
I don't understand this. Generally, engines search the pv node with a full window and the non-pv nodes with a zero window. Pretty much every engine does it like that.cyberfish wrote:For my engine, I think I am doing something different from most engines, and I wonder if there are any drawbacks.
1) I use the transposition table to keep track of PV (the PV printing routine just follows the hash move at each position to get the PV).
That I think can only affect thinking output and not strength, so this is a minor issue.
2) I don't differentiate between root and non-root nodes. When it's the engine's turn to move, it just calls negamax on the root position, and then return the hash move from the transposition table when negamax returns (if not interrupted). My code is carefully written so that the "root" negamax call will always store a hash move in the TT. It also allows clean implementation of aspiration window. Unlike most (actually every I have seen) engines, it doesn't generate a list of legal moves, and call negamax on each resulting position.
If you don't generate all the moves and search them, how do you find the best answer? It is not clear to me what you are doing at all.
Your method will be better if you should miss your guess on the opponent's response. The "skip one ply" method will be better if you guess right on what the opponent's response will be. Heuristically, it appears that "skip one ply" wins but I guess it may do poorly if your move does not match the opponent's very often.
It seems to work quite well for my engine, but does it have any negative impact that I didn't see?
3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
There are some scores as bad as 35% in here:
http://www.computerchess.org.uk/ccrl/40 ... =by+rating
I guess if the engines you match against correlate like that against you, your strategy is better.
This is one case where I think self-testing would be destructive (you *must* test against other engines or the results will be tainted for sure).
I guess that we can call your method 'cautious pondering' and the most often used method 'speculative pondering'. I think it would be valuable to code both methods and test to see which is better. I guess that it may vary from engine to engine. Speculative turned out better for the two engines I tried it on.
Re: Not differentiating root and non-root / pondering approa
Thank you for the reply!
(ignoring the iterative deepening for now)
My way -
I decided to do it this way because I noticed there is some huge code duplication in the root search code and negamax. The code is A LOT simpler for me, but I'm wondering why no one else (that I know of) is doing it this way...
Thanks for the background on speculative vs cautious pondering. I guess for the big guys, speculative works great because they think more or less alike. On the other hand, for weaker engines, every engine has their own good and bad parts of eval, etc, so the ponder hit rate is lower, and cautious way is better?
The conventional way -I don't understand this. Generally, engines search the pv node with a full window and the non-pv nodes with a zero window. Pretty much every engine does it like that.
If you don't generate all the moves and search them, how do you find the best answer? It is not clear to me what you are doing at all.
Code: Select all
Move engine_move() {
MoveList ml = gen_all_legal_moves();
Score best_score = INF;
Move best_move;
for ( i in ml ) {
make_move(i);
Score this_score = negamax();
undo_move(i);
if (this_score > best_score) {
best_score = this_score;
best_move = this_move;
}
}
return best_move;
}
My way -
Code: Select all
Move engine_move() {
negamax;
return hash_move_for_this_position;
}
Thanks for the background on speculative vs cautious pondering. I guess for the big guys, speculative works great because they think more or less alike. On the other hand, for weaker engines, every engine has their own good and bad parts of eval, etc, so the ponder hit rate is lower, and cautious way is better?
-
- Posts: 1922
- Joined: Thu Mar 09, 2006 12:51 am
- Location: Earth
Re: Not differentiating root and non-root / pondering approa
For me, and I suspect for most complex engines, the root search and the normal search have about 0% code in common. My root search has a different type of move list, displays pvs, doesn't do extensions or reductions, and updates several statistics unique to the root. Additionally, since my search is iterative, the root search has to set up the search stack.
-
- Posts: 20943
- Joined: Mon Feb 27, 2006 7:30 pm
- Location: Birmingham, AL
Re: Not differentiating root and non-root / pondering approa
You are throwing away a lot of processing time. You should average at _least_ 50% on ponder hits over the course of a game, correctly predicting the opponent's move thru your PV. Searching from the opponent's perspective simply costs you one ply that you would be getting if you ponder the best move you found as most do...cyberfish wrote:For my engine, I think I am doing something different from most engines, and I wonder if there are any drawbacks.
1) I use the transposition table to keep track of PV (the PV printing routine just follows the hash move at each position to get the PV).
That I think can only affect thinking output and not strength, so this is a minor issue.
2) I don't differentiate between root and non-root nodes. When it's the engine's turn to move, it just calls negamax on the root position, and then return the hash move from the transposition table when negamax returns (if not interrupted). My code is carefully written so that the "root" negamax call will always store a hash move in the TT. It also allows clean implementation of aspiration window. Unlike most (actually every I have seen) engines, it doesn't generate a list of legal moves, and call negamax on each resulting position.
It seems to work quite well for my engine, but does it have any negative impact that I didn't see?
3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
-
- Posts: 778
- Joined: Sat Jul 01, 2006 7:11 am
Re: Not differentiating root and non-root / pondering approa
In another thread recently, you stated that most of the time in a search is spent on the PV, so the loss of time caused by searching from the opponent's perspective would not be that great. It could be worth a test just to see how many ELO difference it makes.bob wrote:You are throwing away a lot of processing time. You should average at _least_ 50% on ponder hits over the course of a game, correctly predicting the opponent's move thru your PV. Searching from the opponent's perspective simply costs you one ply that you would be getting if you ponder the best move you found as most do...cyberfish wrote:For my engine, I think I am doing something different from most engines, and I wonder if there are any drawbacks.
1) I use the transposition table to keep track of PV (the PV printing routine just follows the hash move at each position to get the PV).
That I think can only affect thinking output and not strength, so this is a minor issue.
2) I don't differentiate between root and non-root nodes. When it's the engine's turn to move, it just calls negamax on the root position, and then return the hash move from the transposition table when negamax returns (if not interrupted). My code is carefully written so that the "root" negamax call will always store a hash move in the TT. It also allows clean implementation of aspiration window. Unlike most (actually every I have seen) engines, it doesn't generate a list of legal moves, and call negamax on each resulting position.
It seems to work quite well for my engine, but does it have any negative impact that I didn't see?
3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
-
- Posts: 318
- Joined: Thu Mar 09, 2006 1:07 am
Re: Not differentiating root and non-root / pondering approa
I do it this way also. But I am always told that is not good.cyberfish wrote:3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
Though nobody tries to explain in depth why. See this thread:
http://www.talkchess.com/forum/viewtopi ... 34&t=24870
Harald
-
- Posts: 3196
- Joined: Fri May 26, 2006 3:00 am
- Location: WY, USA
- Full name: Michael Sherwin
Re: Not differentiating root and non-root / pondering approa
RomiChess also does it this way.Harald wrote:I do it this way also. But I am always told that is not good.cyberfish wrote:3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
Though nobody tries to explain in depth why. See this thread:
http://www.talkchess.com/forum/viewtopi ... 34&t=24870
Harald
My thinking is that if 90% of the time is spent on the first root move then most of the deeper hash entries gained is for that root move which is the same as a guess move. The rest of my thinking is that I would rather have some information on every ponder than just on the correct guesses. Also I am too lazy to try the other way.

If you are on a sidewalk and the covid goes beep beep
Just step aside or you might have a bit of heat
Covid covid runs through the town all day
Can the people ever change their ways
Sherwin the covid's after you
Sherwin if it catches you you're through
Just step aside or you might have a bit of heat
Covid covid runs through the town all day
Can the people ever change their ways
Sherwin the covid's after you
Sherwin if it catches you you're through
-
- Posts: 20943
- Joined: Mon Feb 27, 2006 7:30 pm
- Location: Birmingham, AL
Re: Not differentiating root and non-root / pondering approa
You are losing a whole ply, I would think it easy to see why. Because you are searching for the best move for the opponent, rather than yourself, that ply is important. What it means is that for whatever percent of the time you correctly predict, you will be searching 1 ply less than when you do not predict correct. one ply is measurable in terms of lost Elo...jwes wrote:In another thread recently, you stated that most of the time in a search is spent on the PV, so the loss of time caused by searching from the opponent's perspective would not be that great. It could be worth a test just to see how many ELO difference it makes.bob wrote:You are throwing away a lot of processing time. You should average at _least_ 50% on ponder hits over the course of a game, correctly predicting the opponent's move thru your PV. Searching from the opponent's perspective simply costs you one ply that you would be getting if you ponder the best move you found as most do...cyberfish wrote:For my engine, I think I am doing something different from most engines, and I wonder if there are any drawbacks.
1) I use the transposition table to keep track of PV (the PV printing routine just follows the hash move at each position to get the PV).
That I think can only affect thinking output and not strength, so this is a minor issue.
2) I don't differentiate between root and non-root nodes. When it's the engine's turn to move, it just calls negamax on the root position, and then return the hash move from the transposition table when negamax returns (if not interrupted). My code is carefully written so that the "root" negamax call will always store a hash move in the TT. It also allows clean implementation of aspiration window. Unlike most (actually every I have seen) engines, it doesn't generate a list of legal moves, and call negamax on each resulting position.
It seems to work quite well for my engine, but does it have any negative impact that I didn't see?
3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
-
- Posts: 20943
- Joined: Mon Feb 27, 2006 7:30 pm
- Location: Birmingham, AL
Re: Not differentiating root and non-root / pondering approa
It is obvious why it is bad. Let's take two cases:Harald wrote:I do it this way also. But I am always told that is not good.cyberfish wrote:3) pondering. Instead of guessing opponent's move and thinking on the resulting position like just about every engine under the sun does, my engine just "think as the opponent", filling up the hash table.
I decided to do it this way because I noticed that, for "quiet" positions, ponder hits are quite rare, and the whole effort would be wasted if the opponent doesn't make the predicted move (or 2), and for "violent" positions (recaptures for example), it doesn't really matter anyways.
What are the real world differences between these two approaches in terms of strength?
Many thanks
Though nobody tries to explain in depth why. See this thread:
http://www.talkchess.com/forum/viewtopi ... 34&t=24870
Harald
(1) you predict the wrong move. Neither approach will help here. Your previous search had the wrong expected move from your opponent, so that is no good. The approach being discussed finds a move that is different from what the opponent played, so that is no good. In this case, it is a "tie".
(2) you predict the correct move. If you use traditional pondering, you chose the second move from the PV, played it, and did a normal N-ply search after this move and when the opponent moves, you have a move ready, searched to the normal depth, very quickly after he moves. If you use your approach, you do a normal N ply search to find the best move by your opponent. If he makes this move, you can play the second move in the PV, but it was only searched to depth N-1, which is a loss of one full ply.
Which is better? A normal program will correctly predict opponent moves well over 50% of the time. The last time I posted analysis here it was probably closer to 75%. So with traditional pondering, 75% of the time you get an almost instant move and save time, or you search an extra ply or so if you want to use the time you could save. With the discussed approach, 75% of the time you lose a ply over the other method. Which do you think is better???