Talk:Yatagan/Source

From Robowiki
Jump to navigation Jump to search

Contents

Thread titleRepliesLast modified
Some update ideas013:52, 19 May 2024
1.2.02102:50, 14 June 2013
Improvements1514:01, 29 May 2013
Tuning219:26, 19 May 2013
Sweeping Changes419:48, 25 April 2013
Crazy Ideas2112:44, 4 April 2013
Development Version107:53, 22 March 2013
Random Chance of Reversing821:53, 21 March 2013

Some update ideas

  • Adjusting energy drop table to oscillate when the enemy fires the same tick as a bullet hit (and possibly some wall hits).
  • Changing the pattern matching search to a do-while loop to save 3 bytes. (I vaguely remember testing this years ago. Compiler update?)
  • Rounding lateral velocities for better accuracy against bots like Acero. (I haven't carefully tested how this changes scores.)
Sheldor2 (talk)13:52, 19 May 2024

This looks really cool! The only problem I can see is if the bullet power is below 1, it won't react to fire in the oscillate mode. I also fixed a tiny problem in the number of values in the REVERSE_ON_ENEMY_FIRE block.

Skilgannon (talk)11:04, 4 June 2013

Interesting. Is this functionally different or just for the codesize?
If so how much is it saving?
I remember trying something similar to remove a conditional and replace it with a formula and it came out larger so I ditched the idea. Admittedly I was doing something a little different, but cool if you have gotten it to work for you and gained codesize.

Nz.jdc (talk)13:20, 4 June 2013

I'm curious, what did you try?

Sheldor (talk)03:06, 5 June 2013
 

I noticed the problem with casting the energy drop to an int, but I figured that if an enemy was firing power 1s at a distance of around two hundred pixels, we would be able to get a score of 80+%, even with RM.

@Nz.jdc
This method saves two bytes over the conditional method (just enough to fit setAdjustGunForRobotTurn(true)). I don't think it is functionally different from a conditional check. If it is, I probably did something wrong.

Off Topic: I don't understand how your new Adept movement works. What's the point of moveMode ^= 1? Wouldn't that just return moveMode unchanged?

Sheldor (talk)18:15, 4 June 2013

The old neophyte movement changed moveMode from 1 to -1 and back on every bullet hit. Then used direction *= moveMode to flip between orbit mode and oscillate mode whenever we get hit.

The new adept movement keeps that, but combines it with a yatagan style onDeath lookup table. However note that in adept onDeath uses moveMode += 2. ^ is the XOR operator, so on every bullet hit we toggle the low bit. This allows it to combine pure orbit, switch on death to pure oscillate. Do that a few times as yatagan does, then after several deaths it will go back to toggling between orbit and oscillate on every hit.

Nz.jdc (talk)23:36, 4 June 2013

D'oh! I thought that carets were exponentiation operators. Your movement makes much more sense to me now that I realize they are inequality checks.

Sheldor (talk)03:04, 5 June 2013

Sorry for being all pedantic about it, but I just wanted to make sure you understood that XOR isn't an inequality check.

if you have two numbers say:

a=1000101;

b=1011110;

then c=a^b; sets each bit of c to 1 iff that bit in a is one or that bit in b is 1 but not both. Otherwise the bit is set to 0. So c==0011011 is true.

Again. Sorry for being pedantic but I wanted to make sure that this was clear.

AW (talk)18:02, 6 June 2013

Thanks.

Sheldor (talk)19:26, 6 June 2013
 
 
 

I ran some tests, and it looks like we'd only get a score in the sixties. I'm not worried though, because I don't know of a single bot in the rumble that would fire bullets less than power 1.0 at close range, except in the endgame. And even if there was one, it would likely have a HOT gun, which would be dodged by orbit movement anyway.

Sheldor (talk)17:15, 10 June 2013

Well, let's see how it does! =)

Skilgannon (talk)20:17, 12 June 2013

Hmm, apparently not quite as good as 119. The scores may not have quite stabilised yet, but it has dropped down to second with 78.06 APS, about -1.2 IIRC :(

On the plus side I briefly get to retake the lead :)

Not to worry though, I have the superlatively evil (nasty, unpleasant, dishonourable, cheating or the insult of your choice) version 1.2 of PralDeGuerre under development. Now if only it performs up to the statistical predictions...

Nz.jdc (talk)23:07, 12 June 2013

By the way, how much space is that move change saving? I think Sheldor said 2 bytes.
An alternative that might perform better (can't say for sure, you would have to benchmark it) would be to use the old move, but change the "... - (1.1 - 1e-8) ) <= 1)" to "... - 1) <= 2)".
This is slightly less accurate as the energy detect is .001..3.999 rather than .001..3.001, but it could work better.
You would also need to update the rand chance to be "4 / 0.6*Math.sqrt(..." rather than "3.0/(0.6*Math.sqrt(.." to account for the wider window.

Nz.jdc (talk)23:25, 12 June 2013
 

The drop in score is due to two problems with the table. I just fixed both of them.

Yep, this method of enemy fire detection is two bytes smaller than the previous. The other char based check you just posted would be (going by memory here) only one byte smaller than the original, which would be one byte bigger than my new method.

Sheldor (talk)00:56, 13 June 2013
 
 
 
 
 

Improvements

Wow! This is probably the closest a stable PM bot has ever gotten to dethroning LBB 1.69e. It only has about .3 APS to go!

It seems like we could gain that much just by fine-tuning constants. Any suggestions?

Sheldor16:26, 28 April 2013

Yeah, clearly less aggressive distancing and bullet power helps out a bunch here. Now that we've changed the default distance we also need to change the reverse probability, all those need to go to 29. Also, I really wonder if there isn't some way to reduce the number of sacrifice rounds at the beginning against top-bots. Perhaps have something like what I do in Toorkild with using total enemy damage received to trip the movement modes instead of number of deaths.

Skilgannon21:52, 28 April 2013

Hmm, fewer exploitative rounds would almost certainly increase PL--er, PWIN, but it might reduce APS against weak bots. I suppose we could try going back to four rounds of exploitative movement and see if that helps.

I don't see any plausible mode-selection other than the one we have now. The amount of Codesize we have to work with is far too small to even implement something like Splinter's, let alone Toorkild's.

Sheldor23:47, 28 April 2013
 

You could always enter a few new bots that LBB doesn't have data on. ;) Seems kinda cheap, but hey, you live by the black book, you die by the black book...

Voidious23:09, 28 April 2013

Not with any particular intent, but I have been helping in this direction by updating my nanobots and adding a few new ones ;-)
There is at least one more under development which should eventually get uploaded provided the idea doesn't completely fail in benchmarking.

Nz.jdc (talk)14:11, 27 May 2013
 

I wonder what would happen to the ranking if hideEnemyNames was set to true.

MN15:26, 29 April 2013
 

Would we be able to save a few bytes by eliminating unnecessary casting? For instance, we could make BULLET_POWER an int constant so the anti-ram doesn't have to be cast to a double. (Plus, 2 hard-coded as an int is two bytes cheaper than 2 hard-coded as a double.) Also, we could make DISTANCE_FACTOR a double constant so it doesn't get cast as a double when we use it to divide getVelocity().

I'm somewhat surprised by the ~0.1% drop in APS after changing match length reduction. It seems it tried too hard to predict random movement and got fooled more easily. I guess we'll go back to 1.1.4's method, unless you have any other ideas.

Sheldor (talk)02:39, 27 May 2013

I don't think a much longer match length so much predicts random movement as it does oscillators that don't use random numbers.

Anyway, I made those changes, and the bullet power one saves us a single byte. Not sure what to do with two bytes though...

Skilgannon (talk)07:47, 27 May 2013

I might have another byte for you. I have been doing some experimenting my my movement code and obviously also looking at yatagan since it is the best. One tweak I have tried (but not yet benchmarked or verified) that looks like it saves one byte is to not use infinity for direction. This then allows you to use direction rather than getVelocity() in the turning code, which should save a byte. Something like:

 private final static double VERY_BIG            = 1e+200;
private final static double CLOSE_FACTOR = VERY_BIG * 430;
...
turnRadarRightRadians(direction = VERY_BIG);
...
setTurnRightRadians(Math.cos((rd = e.getBearingRadians()) - (e.getDistance() - PREFERRED_RANGE) * (direction / CLOSE_FACTOR)));


This should work provided there is nothing weird in the robocode radar which will cause issues without the infinity.

Nz.jdc (talk)14:07, 27 May 2013

That's a very cool idea. The only thing I'd be concerned about is the radar, since it will subtract the amount it turns from the getRadarTurnRemainingRadians() and could eventually run out (although not really an issue if it is 1e200). Perhaps by reading in degrees and writing in radians for the infinity lock we could negate that, though. In fact, we could probably get away with a smaller value. I'll give it a spin when I get home.

Skilgannon (talk)14:24, 27 May 2013

Looks like it works ok. I was worried about depletion too, especially when I saw you use 48 (any reason for that number in particular?), then I actually thought about it and noted the rad/deg growth, so anything down to 2PI should be ok :)

Nz.jdc (talk)01:45, 29 May 2013
 
 
 
 

Is there any way we could store a negative char value and get rid of the

- (1.1 - 1e-8)

code?

Sheldor (talk)19:11, 27 May 2013

I don't think so. That is there for the bullet detection, and the char value is multiplied by the random so if we used it for bullet detection it wouldn't be reliable. We're down to 246 bytes though, so any ideas of what else to add?

I think I identified where the score difference between 1.1.6 and 1.1.4 crept in, it was from Yatagan stopping if the radar slipped. My local tests show that increasing the direction to 48 fixes the bots that had the biggest score discrepancies.

Skilgannon (talk)20:09, 27 May 2013
 
 

I'm putting out those latest changes now, but there are some things I want to try in isolation (ie. no other changes):

  • Putting orbiting first instead of oscillating (I'm not sure if the improved score came from that or the anti-ram)
  • Making the reversing constant bigger and smaller (just for kicks, since that is originally tuned for GF bots and we are dealing with PM)

I also think there might be some points that can be gained in embedding some common StopNGo patterns and orbiting patterns in the initial gun string.

Any other ideas?

Skilgannon21:43, 4 May 2013

Well, firing power 2's most of the time seems to work well for Sabreur, Caligula, and Fuatisha.

Sheldor21:50, 4 May 2013

Ah, yeah, good one, since we don't have to worry about rambots now.

Skilgannon21:52, 4 May 2013
 
 

Sweeping Changes

While it isn't my robot to criticize, but I found making to many changes at once can be dangerous. As you cannot be sure what influenced your score.

It actually should be obvious, but until it bites you enough...

Chase18:02, 25 April 2013

Thanks. I considered tweaking just one thing at a time, but I figured that since all the changes shared the same purpose (making the bot more cautious and conservative), they would have similar effects.

Sheldor18:23, 25 April 2013
 

Well it doesn't always work exactly the way you expect. :)

But as I said, not my robot, just a bit of unasked for advice.

Chase18:46, 25 April 2013

I don't mind advice. Skilgannon and I are having all our developmental discussions on a public wiki after all. If you ever see something that should be pointed-out, then please, go ahead and point it out.

Sheldor18:55, 25 April 2013
 

Updating one thing at a time between submits to the rumble helps you track the effect of each improvement separately. The final result is sometimes different from small scale test beds.

At the same time, multiple improvements which only work together might never make it to the rumble.

For example:

- Wave surfing/Precise Prediction without a strong danger function is inferior to shrapnel dodging.

- Advanced dodging and targeting in melee sometimes don´t work because of weak melee radar.

- Adding more classifiers to k-NN search not working due to bad tuning.

- Fixing a Performance Enhancing Bug hurts the score unless you combine another improvement to take advantage of the fix.

MN19:48, 25 April 2013
 

Crazy Ideas

Edited by author.
Last edit: 14:08, 22 March 2013

First, we initialize integer to 255 to save a byte. :)
Then, in the PM code we use (integer = integer >> 1), instead of (integer = integer - 1).

If I'm right (which I rarely am), this would be smaller, faster and smarter. How does it sound to you?

Sheldor12:51, 22 March 2013

Sounds good. I did a geometric reduction of the key length in Toorkild as well, and it worked fine.

Skilgannon12:58, 22 March 2013
 

Hmm, for some reason, under Jikes, both of those changes add a byte of codesize. Any number above 127 takes an extra byte, and >> is one more byte than --

Skilgannon15:13, 22 March 2013

Were you using Jikes when you compiled Toorkild and got the weird savings from 255?

Sheldor15:35, 22 March 2013
 

Yes, but I was using it for an array size, so that might have been something else happening.

Skilgannon16:15, 22 March 2013
 

So, if we do it just like Toorkild and use 64 as the initialization value, and use integer /= 2 instead of --integer, we should break even at 249 bytes, right?

Also, I think we should try using power-3 bullets, or at least go back to power 2.6667. I think 2.33333... is a little too soft for a bot with such an aggressive movement.

If the changes work, then go ahead and release version 1.0.4.

Sheldor17:23, 22 March 2013
 

integer/=2 takes an extra byte from --integer, but if we switch our bullet power to 3 we have that byte to spare. I'll package it up and release.

Skilgannon17:43, 22 March 2013
 

Huh, for some reason it lost a lot against weak bots. Do you think this is because of the PM change, the bullet power change, or the movement change? I doubt it was because of the change to the random multiplier, because the RM shouldn't even be activated against weak bots.

Sheldor20:39, 22 March 2013
 

I think the higher bullet power made it waste energy quicker, giving it an extra loss or two, which pushed a bunch of bots over into the random movement instead of orbit/oscillate.

One thing I noticed while watching battles was if it starts from very far away it does loops instead of settling for a nice orbital movement. I'm thinking of decreasing the turn amount caused by the distancing, especially as it isn't as sensitive to that now that the gun can handle any distance correctly.

Skilgannon21:02, 22 March 2013

Okay. Let's change the BP back to 2.33... and the constant in the distance controller from 2500 to 3000.

We also might try doing 3/orbit + 3/oscillate + 94/random instead of 2/orbit + 2/oscillate + 96/random.

Sheldor22:57, 22 March 2013
 

One step at a time, I'd rather have less sacrificial rounds against top bots and lower the bullet power, although that gets us right back to where we were. I also want to see where the threshold is, so how about BP 2.666?

Skilgannon07:15, 23 March 2013

Sounds good.

Sheldor13:19, 23 March 2013
 
 

I have another crazy idea that would allow us to get rid of the distance variable. The problem is, it would cost about ~2 bytes in other areas. Should I try it?

Sheldor16:26, 2 April 2013
 

Of course, give it a go. I'll see how it compiles.

Skilgannon22:36, 2 April 2013
 

Sweet, that saves 3 bytes, down to 246. I'll package and upload in the morning when I'm a bit more awake =)

Skilgannon23:38, 2 April 2013
 

Ok, that doesn't work because the absoluteBearing has been fully initialised and doesn't just use the e.getBearingRadians() value, so it goes in circles. Oh well, I was hoping for some more codesize there!

Skilgannon19:26, 3 April 2013

Try it again with a pair of parentheses around e.bearing + heading. That should fully initialize absolute bearing. If it doesn't, then there must be something else going on.

What were you planning to do with the extra space?

Sheldor20:21, 3 April 2013

Nope, the problem is in the distancing, see the change I made that fixes the behaviour.

I'm not sure what to do with the space, but I'm sure we can think of something. Perhaps better bullet power selection for rambots or something like that.

Skilgannon20:28, 3 April 2013

I think I figured out a way to get those bytes back--at a loss of targeting accuracy. We'll see if it's worth it.

I highly doubt you'd be able to fit anti-ram in 3-4 bytes. But, it seems that almost every time I say that, you prove me wrong. :)

Sheldor21:19, 3 April 2013

Ooooh, that is ugly ugly ugly. But this is nano, the king of ugly, so it would only be fitting if the king was ugly too. I'm not sure what we'd gain from rambots would make up for this, but it's worth a try I guess.

Skilgannon09:58, 4 April 2013
 
 
 
 
 

Development Version

Skilgannon,
I think that it would be best to use the Development Version section as the main development code base. Sort of like how Chase and I managed the co-development of Talon. That is, whenever either of us tweaks Yatagan, we update the code on this page. And, whenever we decide to release a new version, we package the code on this page.

Also, I would appreciate if you posted the code-size after you change something.

Thanks.

Sheldor02:28, 22 March 2013

No problem.

Skilgannon07:53, 22 March 2013
 

Random Chance of Reversing

I think it would be best if we change the default chance-of-reversing in RM mode from 0.666667 back to 0.5.

Sheldor01:13, 21 March 2013

Done. This is something which will need some tuning, though. And how about a larger orbit distance?

Skilgannon08:48, 21 March 2013
 

The HOT avoidance likes to be really close to minimize wall hits, the LT avoidance really doesn't care how close it is, and the RM mode likes to stay just about as far away as possible.

Both Moebius and Sabreur use 160, and I believe Mike said that after a lot of testing, he found that 160 was the best distance for Moebius.

But, if you would like to try 180 or 200, go ahead.

Sheldor12:22, 21 March 2013
 

Huh, apparently 0.6666666666667 was about 0.4 APS better than 0.5.

Do you have any idea why it's performing so horribly against other PM bots?

Sheldor17:28, 21 March 2013
 

Those two oddities are linked. Because it only decides once per enemy bullet which direction to go in, and because of the close fighting distance, we end up with two large probability spikes, one at GF1 and one at GF-1 (or as close as is reachable). If it were further away more than one bullet firing event would happen, so it would make the decision more than once, adding variability to where it ends up (2^n spikes for n bullet firings). Either we need to take the reversing decision out of the bullet-fired dependency, or we need to be far enough away that it can even out those spikes.

Skilgannon17:55, 21 March 2013

PM doesn't care about GF's, but a movement that is easy for a GFT gun to hit is usually easy for a PM gun to hit.

If you could fit a .08 probability of reversing every tick without loosing performance elsewhere, that would be amazing. The reason Yatagan's movement is small enough to fit distance control and good energy monitoring is because it's so simple and elegant. When the enemy fires, either never reverse, always reverse, or have a random chance of reverse or not reversing.

I guess we'll try a distance of 200/220 in the next version. It will almost certainly harm performance against HOT, but the gain against PM might make up for it.

Sheldor18:25, 21 March 2013
 

I think I might have something which keeps full functionality but also reverses with a 0.08 probability. The problem is, it also reverses with any enemy bullet fire, so should I decrease that probability? I'm thinking down to about 0.06, since there needs to be a good chance of a direction change happening during the flight time of the bullet, but there was already one at bullet fire time so we don't want it reversing all over the place. Or should I stick with 0.08?

Skilgannon21:03, 21 March 2013

Go ahead and test with 0.06 or 0.05.

Sheldor21:35, 21 March 2013
 

Never mind, I figured out a way around that too, all while using even less codesize than our previous reverse method, so I added back setAdjustGunForRobotTurn(true). Being able to feed custom variables to a random multiplier can do miraculous things! Particularly when you only want probabilistic behaviour, and not absolute behaviour. But hey, a probability of 1 in 20k is pretty much 0, right? ;-)

Skilgannon21:53, 21 March 2013