Robo Home | Radar | Changes | Preferences | AllPages

Difference (from prior major revision) (author diff)

Changed: 63c63
double radaroffset = ((getOthers() == 1 && timeSinceLastScan? < 3)?robocode.util.Utils.normalRelativeAngle(getRadarHeadingRadians?() - enemyAbsoluteBearing?):Double.POSITIVE_INFINITY)<0);
double radaroffset = (getOthers() == 1 && timeSinceLastScan? < 3)?robocode.util.Utils.normalRelativeAngle(getRadarHeadingRadians?() - enemyAbsoluteBearing?):Double.POSITIVE_INFINITY);

Here's a bot implementing an effective OneOnOne radar, without regard to CodeSize. In Melee it will simply spin. Many good melee bots uses a simple spinning radar like that. If I remember correctly even the mighty TheArtOfWar. -- PEZ
public class RadarBot extends AdvancedRobot {
    private int timeSinceLastScan = 10;
    static double enemyAbsoluteBearing;

    do {
    } while true;

    public void onScannedRobot(ScannedRobotEvent e) {
        enemyAbsoluteBearing = getHeadingRadians() + e.getBearingRadians();
        timeSinceLastScan = 0;

    private void doScanner() {
        double radarOffset = Double.POSITIVE_INFINITY;
        if(getOthers() == 1 && timeSinceLastScan < 3) {
            radarOffset = robocode.util.Utils.normalRelativeAngle(getRadarHeadingRadians() - enemyAbsoluteBearing);
            radarOffset += sign(radarOffset) * 0.02;

    int sign(double v) {
        return v > 0 ? 1 : -1;
This is not by any means a radar meant for minibots since it consumes way to much codesize for that. Still, it's the radar used by Tityus, which leaves some room for imporvement of that bot. -- PEZ

Thanks for the code example pez, this will be easy enough to get into my Micro, I have like 150 codesize to burn :) but I know I should shrink some of the stuff I have down. It isnt very compressed as it is. -- Dan724

why do you need to keep track of "timeSinceLastScan" ? --SSO?

Sometimes the radar "slips" and then I need to spin the radar full turn. Or that's the theory. I have not tried without this. Does it work? -- PEZ

If you don't do that, you need to account for the beginning of the round. -- Kawigi

What does the sign function do? I'm not familiar with the syntax. Thanks. -- Tango

It just returns 1 for positive numbers and -1 for negative numbers or zero. It's good for knowing in what "direction" this or that observation is going. -- PEZ

Is that some kind of special java short version of if/then/else? :-/ I really should learn java properly... -- Tango

You could see it as a short for if/then/else. But it's nothing specifically Java about it. The function is actually defined last in that code snippet. Look closer. =) I would say that it's more a math thing if it wasn't that I think you should return zero for a zero value then. I could have used an if/then/else structure, but I don't think it would have been as readable. -- PEZ

I was looking at the function definition. I just don't recognise the syntax with question marks and colons and suchlike. :-/ As i say, i should probably learn java. -- Tango

Ah! Sorry, I misunderstood the question. The question-mark and colon is sort-of a Java short for if/then/else indeed. It's called the trinary condition operator. It's inherited from C. Since lots and lots of programming languages take a lot of inspiration from the C syntax this operator exists in many languages. A similar thingy exists in the macro language of Excel if you are more familiar with that. There it's a function "immediate if()" named IIF(condition, result-if-true, result-if-false). So you read the statement in that sign() function like so: "If the value ''v" is greater than 0 - return 1, else return -1. -- PEZ

Unlike an if/then/else this does not /do/ anything, it merely selects between which of two values to "show" to the statement outside it. Ie:

if(blah) do_something();
is legal.
is not, unless do_something() and do_somethingelse() return values, and even then the trinary condition needs to be assigned somewhere, it can't be a standalone statement. -- Kuuran

Anyone thought of squeezing the code into a smaller space? :

    private void doScanner() {
        double radaroffset = (getOthers() == 1 && timeSinceLastScan < 3)?robocode.util.Utils.normalRelativeAngle(getRadarHeadingRadians() - enemyAbsoluteBearing):Double.POSITIVE_INFINITY);
        setTurnRadarLeftRadians(radaroffset * (radaroffset > 0 ? 1.02 : 0.98 ));

-- nfwu

I do not think this is smaller in codesize, and certainly not more readable. -- GrubbmGait

I mainly use a radar that determines how much it should turn to be exactly aimed at the enemy and then add a few degrees to keep it from slipping. I have only seen it completely slip once or twice (I do have some anti-radar slip code so that accounts for a few). I am not sure about the exact codesize but it is around 80. Of course the following code is the core of mine but...

	double turnRadar = Utils.normalRelativeAngle(Utils.angleFromPoint(myX, myY, enemyX, enemyY) - radarHeading);
	if (others == 1)
		turnRadar += ((turnRadar >= 0)? 2: -2);
		turnRadar += ((turnRadar >= 0)? 45: -45);
	return turnRadar;

It does not work to well for melee but the if statement can be changed from having a very large angle to spinning like this:

	double turnRadar = Utils.normalRelativeAngle(Utils.angleFromPoint(myX, myY, enemyX, enemyY) - radarHeading);
	if (others == 1)
		turnRadar += ((turnRadar >= 0)? 2: -2);
		turnRadar = 360;
	return turnRadar;

(Note: The code uses degrees.)

-- Kinsen

Robo Home | Radar | Changes | Preferences | AllPages
Edit text of this page | View other revisions
Last edited December 7, 2005 1:48 EST by Nfwu (diff)