// Refresh the output value of the input rows (first NINPUTS of the table) private void RefreshTableInputs(TableRex t) { for (int i = 0; i < TableRexBase.NINPUTS; i++) { switch (i) { case 0: t[i].output = InputVelocity(); break; case 1: t[i].output = InputEnergy(); break; case 2: t[i].output = InputHeading(); break; case 3: t[i].output = InputGunHeading(); break; case 4: t[i].output = InputGunHeat(); break; case 5: t[i].output = InputRadarHeading(); break; case 6: t[i].output = InputRadarTurnRemaining(); break; case 7: t[i].output = InputDistanceToWestWall(); break; case 8: t[i].output = InputDistanceToNorthWall(); break; case 9: t[i].output = InputDistanceToEastWall(); break; case 10: t[i].output = InputDistanceToSouthWall(); break; case 11: t[i].output = InputConstant1(); break; case 12: t[i].output = InputConstant2(); break; case 13: t[i].output = InputConstant10(); break; case 14: t[i].output = InputConstant90(); break; case 15: t[i].output = InputEnemyVelocity(); break; case 16: t[i].output = InputEnemyEnergy(); break; case 17: t[i].output = InputEnemyHeading(); break; case 18: t[i].output = InputEnemyBearing(); break; case 19: t[i].output = InputEnemyDistance(); break; default: break; } } }
private double Or(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando Or con " + i1.ToString() + ", " + i2.ToString()); return LogicOperators(t, i1, i2, LogicOps.or); }
private double RandomFloat(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando RandomFloat con " + i1.ToString() + ", " + i2.ToString()); Random rand = new Random((int)X % ((int)Energy + 1) + (int)Time); return (rand.NextDouble() * t[i1].output + t[i2].output); }
public override void Run() { // Reading the data from the file string rawBin = ""; try { using (Stream count = GetDataFile(Name + ".rxt")) { if (count.Length != 0) { using (TextReader tr = new StreamReader(count)) { rawBin = tr.ReadToEnd(); //Out.WriteLine("rawBin = " + rawBin); // DEBUG //Out.WriteLine("rawBin = "); // DEBUG // OUT DEBUG //rawBin.Trim(char.Parse(TableRexBase.SEPARATOR)); //string[] rows = tRaw.Split(char.Parse(TableRexBase.SEPARATOR) // OUT DEBUG } } } } catch (Exception) { Out.WriteLine("Could not read the TableRex table."); } rawBin = rawBin.Trim(char.Parse(TableRexBase.TSEPARATOR)); string[] tables = rawBin.Split(char.Parse(TableRexBase.TSEPARATOR)); if (tables.Length != 5) { Out.WriteLine("Invalid file data. Five (5) programs (sections sepparated by \"|\") are needed."); return; } for (int i = 0; i < tables.Length; i++) { switch (i) { case 0: mainTable = new TableRex(tables[i]); break; case 1: onScannedTable = new TableRex(tables[i]); break; case 2: onHitByBulletTable = new TableRex(tables[i]); break; case 3: onHitBotTable = new TableRex(tables[i]); break; case 4: onHitWallTable = new TableRex(tables[i]); break; } } while (true) RunProgram(TableRexPrograms.main); //Out.WriteLine("Transformando 101110011110101100 en int: " + Support.BinaryStringToInt("101110011110101100").ToString()); // DEBUG }
private double Not(TableRex t, int i1) { //Out.WriteLine("Ejecutando Not con " + i1.ToString()); return LogicOperators(t, i1, 0, LogicOps.not); }
private double Add(TableRex t, int i1, int i2) { /*Out.WriteLine("Ejecutando Add con " + i1.ToString() + ", " + i2.ToString());*/ return (t[i1].output + t[i2].output); }
private double NormalizeRelativeAngle(TableRex t, int i1) { //Out.WriteLine("Ejecutando NormalizeRelativeAngle con " + i1.ToString()); // Source: http://www.java2s.com/Tutorial/Java/0120__Development/Normalizesanangletoarelativeangle.htm //return (t[i1].output %= 360) >= 0 ? (t[i1].output < 180) ? t[i1].output : t[i1].output - 360 : (t[i1].output >= -180) ? t[i1].output : t[i1].output + 360; return Robocode.Util.Utils.NormalRelativeAngleDegrees(t[i1].output); }
private double LessThan(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando LessThan con " + i1.ToString() + ", " + i2.ToString()); if (t[i1].output < t[i2].output) return 1; return 0; }
private double LogicOperators(TableRex t, int i1, int i2, LogicOps op) { bool b1 = true; bool b2 = true; bool r = true; if (t[i1].output < 1) b1 = false; if (t[i2].output < 1) b2 = false; switch (op) { case LogicOps.and: r = b1 && b2; break; case LogicOps.or: r = b1 || b2; break; case LogicOps.not: r = !b1; break; default: return 0; } if (r) return 1; return 0; }
private double Equal(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando Equal con " + i1.ToString() + ", " + i2.ToString()); if (t[i1].output == t[i2].output) return 1; return 0; }
private double GenerateConstant(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando GenerateConstant con " + i1.ToString() + ", " + i2.ToString()); return i2 - i1; }
private double Divide(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando Divide con " + i1.ToString() + ", " + i2.ToString()); if (t[i2].output != 0) return (t[i1].output / t[i2].output); return (t[i1].output / (t[i2].output + 1)); }
private double ControlActuator(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando ControlActuator con " + i1.ToString() + ", " + i2.ToString()); //Ahead(GenerateConstant(i1, i2)); // DEBUG switch (i1) { case 0: return ActAhead(t[i2].output); case 1: return ActAhead50(); case 2: return ActAheadDistanceToCenter(); case 3: return ActAheadHalfDistanceToWestWall(); case 4: return ActAheadHalfDistanceToNorthWall(); case 5: return ActAheadHalfDistanceToEastWall(); case 6: return ActAheadHalfDistanceToSouthWall(); case 7: return ActAheadDistanceToEnemy(); case 8: return ActAheadHalfDistanceToEnemy(); case 9: return ActBack(t[i2].output); case 10: return ActBack50(); case 11: return ActBackDistanceToCenter(); case 12: return ActBackHalfDistanceToWestWall(); case 13: return ActBackHalfDistanceToNorthWall(); case 14: return ActBackHalfDistanceToEastWall(); case 15: return ActBackHalfDistanceToSouthWall(); case 16: return ActBackDistanceToEnemy(); case 17: return ActBackHalfDistanceToEnemy(); case 18: return ActTurnRight(t[i2].output); case 19: return ActTurnRight10(); case 20: return ActTurnRight45(); case 21: return ActTurnRight90(); case 22: return ActTurnLeft(t[i2].output); case 23: return ActTurnLeft10(); case 24: return ActTurnLeft45(); case 25: return ActTurnLeft90(); case 26: return ActTurnToCenter(); case 27: return ActTurnAwayFromCenter(); case 28: return ActTurnToEnemy(); case 29: return ActTurnAwayFromEnemy(); case 30: return ActTurnPerpendicularToEnemy(); case 31: return ActTurnParallelToNearestWall(); case 32: return ActTurnPerpendicularToNearestWall(); case 33: return ActFire(t[i2].output); case 34: return ActFire1(); case 35: return ActFire2(); case 36: return ActFire3(); case 37: return ActTurnGunRight(t[i2].output); case 38: return ActTurnGunRight10(); case 39: return ActTurnGunRight45(); case 40: return ActTurnGunRight90(); case 41: return ActTurnGunLeft(t[i2].output); case 42: return ActTurnGunLeft10(); case 43: return ActTurnGunLeft45(); case 44: return ActTurnGunLeft90(); case 45: return ActTurnGunToCenter(); case 46: return ActTurnGunToEnemy(); default: break; } return 1; }
// TODO: Optimizar esta funcion (demasiado trasiego de ROW...)(Comprobar si se persisten los cambios a los parámetros, para ahorrar devolver una row) private void CallFunction(TableRex t, int trPointer) { //TableRex.Row result = new TableRex.Row(progRow.function, progRow.param1, progRow.param2); switch (t[trPointer].function) { case (int)TableRexBase.FunctionIndex.absolute_value: t[trPointer].output = Absolute(t, t[trPointer].param1); break; case (int)TableRexBase.FunctionIndex.addition: t[trPointer].output = Add(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.and: t[trPointer].output = And(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.division: t[trPointer].output = Divide(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.equal: t[trPointer].output = Equal(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.generate_constant: t[trPointer].output = GenerateConstant(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.greater_than: t[trPointer].output = GreaterThan(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.less_than: t[trPointer].output = LessThan(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.modulo: t[trPointer].output = Modulo(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.multiplication: t[trPointer].output = Product(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.normalize_relative_angle: t[trPointer].output = NormalizeRelativeAngle(t, t[trPointer].param1); break; case (int)TableRexBase.FunctionIndex.not: t[trPointer].output = Not(t, t[trPointer].param1); break; case (int)TableRexBase.FunctionIndex.or: t[trPointer].output = Or(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.random_float: t[trPointer].output = RandomFloat(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.subtraction: t[trPointer].output = Subtract(t, t[trPointer].param1, t[trPointer].param2); break; case (int)TableRexBase.FunctionIndex.control_actuator: t[trPointer].output = ControlActuator(t, t[trPointer].param1, t[trPointer].param2); break; } }
// TODO: Estudiar visibilidad (public, private...) // Runs the selected program once private void RunProgram(TableRexPrograms prog) { //Out.WriteLine("Ejecutando tabla " + prog.ToString()); // DEBUG // Load working table TableRex currentProgram = new TableRex(); switch (prog) { case TableRexPrograms.main: currentProgram = mainTable; break; case TableRexPrograms.onScannedRobot: currentProgram = onScannedTable; break; case TableRexPrograms.onHitByBullet: currentProgram = onHitByBulletTable; break; case TableRexPrograms.onHitRobot: currentProgram = onHitBotTable; break; case TableRexPrograms.onHitWall: currentProgram = onHitWallTable; break; default: currentProgram = mainTable; break; } // Cycle throught every program line for (int trPointer = TableRexBase.NINPUTS; trPointer < TableRexBase.NROWS; trPointer++) { //currentProgram[trPointer] = CallFunction(currentProgram, trPointer); CallFunction(currentProgram, trPointer); //Out.WriteLine(trPointer.ToString() + "> " + currentProgram[trPointer].output.ToString()); // DEBUG } // Persist changes switch (prog) { case TableRexPrograms.main: mainTable = currentProgram; RefreshTableInputs(mainTable); break; case TableRexPrograms.onScannedRobot: onScannedTable = currentProgram; RefreshTableInputs(onScannedTable); break; case TableRexPrograms.onHitByBullet: onHitByBulletTable = currentProgram; RefreshTableInputs(onHitByBulletTable); break; case TableRexPrograms.onHitRobot: onHitBotTable = currentProgram; RefreshTableInputs(onHitBotTable); break; case TableRexPrograms.onHitWall: onHitWallTable = currentProgram; RefreshTableInputs(onHitWallTable); break; default: mainTable = currentProgram; break; } }
private double Modulo(TableRex t, int i1, int i2) { //Out.WriteLine("Ejecutando Modulo con " + i1.ToString() + ", " + i2.ToString()); if ((int)t[i2].output != 0) return ((int)t[i1].output % ((int)t[i2].output)); return ((int)t[i1].output % ((int)t[i2].output + 1)); }
private double Subtract(TableRex t, int i1, int i2) { /*Out.WriteLine("Ejecutando Subtract con " + i1.ToString() + ", " + i2.ToString());*/ return (t[i1].output - t[i2].output); }
private double Absolute(TableRex t, int i1) { /*Out.WriteLine("Ejecutando Absolute con " + i1.ToString());*/ return Math.Abs(t[i1].output); }