def test_multiple_stuns(self): error_msg = "2 StunThrowers stunning 2 Bees doesn't stun each Bee for exactly one turn." stun1 = ants.StunThrower() stun2 = ants.StunThrower() bee1 = ants.Bee(3) bee2 = ants.Bee(3) self.colony.places["tunnel_0_0"].add_insect(stun1) self.colony.places["tunnel_0_1"].add_insect(bee1) self.colony.places["tunnel_0_2"].add_insect(stun2) self.colony.places["tunnel_0_3"].add_insect(bee2) stun1.action(self.colony) stun2.action(self.colony) bee1.action(self.colony) bee2.action(self.colony) self.assertEqual("tunnel_0_1", bee1.place.name, error_msg) self.assertEqual("tunnel_0_3", bee2.place.name, error_msg) bee1.action(self.colony) bee2.action(self.colony) self.assertEqual("tunnel_0_0", bee1.place.name, error_msg) self.assertEqual("tunnel_0_2", bee2.place.name, error_msg)
def test_inheritance(self): """Tests to see if the Long and Short Throwers are actually using the inherited action from the ThrowerAnt. """ old_thrower_action = ants.ThrowerAnt.action old_throw_at = ants.ThrowerAnt.throw_at def new_thrower_action(self, colony): raise NotImplementedError() def new_throw_at(self, target): raise NotImplementedError() failed_long = 0 try: # Test action ants.ThrowerAnt.action = new_thrower_action test_long = ants.LongThrower() test_long.action(self.colony) except NotImplementedError: failed_long += 1 finally: ants.ThrowerAnt.action = old_thrower_action try: # Test throw_at ants.ThrowerAnt.throw_at = new_throw_at test_long = ants.LongThrower() test_bee = ants.Bee(1) test_long.throw_at(test_bee) except NotImplementedError: failed_long += 1 finally: ants.ThrowerAnt.throw_at = old_throw_at if failed_long < 2: self.fail(msg="LongThrower is not using inheritance") failed_short = 0 try: # Test action ants.ThrowerAnt.action = new_thrower_action test_short = ants.ShortThrower() test_short.action(self.colony) except NotImplementedError: failed_short += 1 finally: ants.ThrowerAnt.action = old_thrower_action try: # Test throw_at ants.ThrowerAnt.throw_at = new_throw_at test_short = ants.ShortThrower() test_bee = ants.Bee(1) test_short.throw_at(test_bee) except NotImplementedError: failed_short += 1 finally: ants.ThrowerAnt.throw_at = old_throw_at if failed_short < 2: self.fail(msg="ShortThrower is not using inheritance")
def test_fire_deadliness(self): error_msg = 'FireAnt does not damage all Bees in its Place' test_place = self.colony.places['tunnel_0_0'] bee = ants.Bee(3) test_place.add_insect(bee) test_place.add_insect(ants.Bee(3)) test_place.add_insect(ants.FireAnt()) bee.action(self.colony) self.assertIs(0, len(test_place.bees), error_msg)
def test_queen_place(self): colony_queen = ants.Place('Original Queen Location of the Colony') ant_queen = ants.Place('Place given to the QueenAnt') queen_place = ants.QueenPlace(colony_queen, ant_queen) colony_queen.bees = [ants.Bee(1, colony_queen) for _ in range(3)] ant_queen.bees = [ants.Bee(2, colony_queen) for _ in range(4)] self.assertEqual(7, len(queen_place.bees), 'QueenPlace has wrong bees') bee_armor = sum(bee.armor for bee in queen_place.bees) self.assertEqual(11, bee_armor, 'QueenPlace has wrong bees')
def test_long(self): error_msg = 'LongThrower has the wrong range' ant = ants.LongThrower() self.colony.places['tunnel_0_0'].add_insect(ant) out_of_range, in_range = ants.Bee(2), ants.Bee(2) self.colony.places['tunnel_0_3'].add_insect(out_of_range) self.colony.places['tunnel_0_4'].add_insect(in_range) ant.action(self.colony) self.assertEqual(in_range.armor, 1, error_msg) self.assertEqual(out_of_range.armor, 2, error_msg)
def test_short(self): error_msg = "ShortThrower has the wrong range" ant = ants.ShortThrower() self.colony.places["tunnel_0_0"].add_insect(ant) out_of_range, in_range = ants.Bee(2), ants.Bee(2) self.colony.places["tunnel_0_3"].add_insect(out_of_range) self.colony.places["tunnel_0_2"].add_insect(in_range) ant.action(self.colony) self.assertEqual(in_range.armor, 1, error_msg) self.assertEqual(out_of_range.armor, 2, error_msg)
def test_short(self): error_msg = 'ShortThrower has the wrong range' ant = ants.ShortThrower() self.colony.places['tunnel_0_0'].add_insect(ant) out_of_range, in_range = ants.Bee(2), ants.Bee(2) self.colony.places['tunnel_0_3'].add_insect(out_of_range) self.colony.places['tunnel_0_2'].add_insect(in_range) ant.action(self.colony) self.assertIs(in_range.armor, 1, error_msg) self.assertIs(out_of_range.armor, 2, error_msg)
def test_nearest_bee(self): error_msg = 'ThrowerAnt can\'t find the nearest bee.' ant = ants.ThrowerAnt() self.colony.places['tunnel_0_0'].add_insect(ant) near_bee = ants.Bee(2) self.colony.places['tunnel_0_3'].add_insect(near_bee) self.colony.places['tunnel_0_6'].add_insect(ants.Bee(2)) hive = self.colony.hive self.assertIs(ant.nearest_bee(hive), near_bee, error_msg) ant.action(self.colony) self.assertIs(1, near_bee.armor, error_msg)
def test_nearest_bee(self): error_msg = "ThrowerAnt can't find the nearest bee" ant = ants.ThrowerAnt() self.colony.places["tunnel_0_0"].add_insect(ant) near_bee = ants.Bee(2) self.colony.places["tunnel_0_3"].add_insect(near_bee) self.colony.places["tunnel_0_6"].add_insect(ants.Bee(2)) hive = self.colony.hive self.assertIs(ant.nearest_bee(hive), near_bee, error_msg) ant.action(self.colony) self.assertEqual(1, near_bee.armor, error_msg)
def test_hungry_eats_and_digests(self): hungry = ants.HungryAnt() super_bee, super_pal = ants.Bee(1000), ants.Bee(1) place = self.colony.places["tunnel_0_0"] place.add_insect(hungry) place.add_insect(super_bee) hungry.action(self.colony) self.assertEqual(0, super_bee.armor, "HungryAnt didn't eat") place.add_insect(super_pal) for _ in range(3): hungry.action(self.colony) self.assertEqual(1, super_pal.armor, "HungryAnt didn't digest") hungry.action(self.colony) self.assertEqual(0, super_pal.armor, "HungryAnt didn't eat again")
def test_hungry_eats_and_digests(self): hungry = ants.HungryAnt() super_bee, super_pal = ants.Bee(1000), ants.Bee(1) place = self.colony.places['tunnel_0_0'] place.add_insect(hungry) place.add_insect(super_bee) hungry.action(self.colony) self.assertIs(0, super_bee.armor, 'HungryAnt didn\'t eat') place.add_insect(super_pal) for _ in range(3): hungry.action(self.colony) self.assertIs(1, super_pal.armor, 'HungryAnt didn\'t digest') hungry.action(self.colony) self.assertIs(0, super_pal.armor, 'HungryAnt didn\'t eat again')
def test_double(self): back = ants.ThrowerAnt() thrower_damage = ants.ThrowerAnt.damage fire_damage = ants.FireAnt.damage front = ants.FireAnt() side_back = ants.ThrowerAnt() side_front = ants.ThrowerAnt() armor, side_armor = 20, 10 bee, side_bee = ants.Bee(armor), ants.Bee(side_armor) self.colony.places['tunnel_0_0'].add_insect(back) self.colony.places['tunnel_0_2'].add_insect(self.queen) self.colony.places['tunnel_0_4'].add_insect(bee) self.colony.places['tunnel_1_1'].add_insect(side_back) self.colony.places['tunnel_1_3'].add_insect(side_front) self.colony.places['tunnel_1_4'].add_insect(side_bee) # Simulate a battle in Tunnel 0 (contains Queen) back.action(self.colony) armor -= thrower_damage # No doubling until queen's action self.assertEqual(armor, bee.armor, "Damage doubled too early") self.queen.action(self.colony) armor -= thrower_damage # Queen should always deal normal damage self.assertEqual(armor, bee.armor, "Queen damage incorrect") bee.action(self.colony) # Bee moves forward self.colony.places['tunnel_0_3'].add_insect(front) # Fire ant added back.action(self.colony) armor -= 2 * thrower_damage # Damage doubled in back self.assertEqual(armor, bee.armor, "Back damage incorrect") self.queen.action(self.colony) armor -= thrower_damage # Queen should always deal normal damage self.assertEqual(armor, bee.armor, "Queen damage incorrect (2)") back.action(self.colony) armor -= 2 * thrower_damage # Thrower damage still doubled self.assertEqual(armor, bee.armor, "Back damage incorrect (2)") bee.action(self.colony) armor -= 2 * fire_damage # Fire damage doubled self.assertEqual(armor, bee.armor, "Fire damage incorrect") # Simulate a battle in Tunnel 1 (no Queen) self.assertEqual(side_armor, side_bee.armor, "Side bee took damage") side_back.action(self.colony) side_armor -= thrower_damage # Ant in another tunnel: normal damage self.assertEqual(side_armor, side_bee.armor, "Side back damage incorrect") side_front.action(self.colony) side_armor -= thrower_damage # Ant in another tunnel: normal damage self.assertEqual(side_armor, side_bee.armor, "Side front damage incorrect")
def test_effect_stack(self): stun = ants.StunThrower() bee = ants.Bee(3) stun_place = self.colony.places['tunnel_0_0'] bee_place = self.colony.places['tunnel_0_4'] stun_place.add_insect(stun) bee_place.add_insect(bee) for _ in range(4): # stun bee four times stun.action(self.colony) for _ in range(4): bee.action(self.colony) self.assertEqual('tunnel_0_4', bee.place.name, 'Status effects do not stack') def test_die_the_old_fashioned_way(self): bee = ants.Bee(3) queen = TestProblem9.queen # The bee has an uninterrupted path to the heart of the colony self.colony.places['tunnel_0_1'].add_insect(bee) self.colony.places['tunnel_0_2'].add_insect(queen) queen.action(self.colony) bee.action(self.colony) self.assertIs(False, len(self.colony.queen.bees) > 0, 'Game ended') queen.action(self.colony) bee.action(self.colony) self.assertIs(True, len(self.colony.queen.bees) > 0, 'Game not ended')
def test_inheritance(self): """Tests to see if the ScubaThrower is actually using the inherited action from the ThrowerAnt. """ old_thrower_action = ants.ThrowerAnt.action def new_thrower_action(self, colony): raise NotImplementedError() old_throw_at = ants.ThrowerAnt.throw_at def new_throw_at(self, target): raise NotImplementedError() failed_scuba = 0 try: ants.ThrowerAnt.action = new_thrower_action test_scuba = ants.ScubaThrower() test_scuba.action(self.colony) except NotImplementedError: failed_scuba += 1 finally: ants.ThrowerAnt.action = old_thrower_action try: ants.ThrowerAnt.throw_at = new_throw_at test_scuba = ants.ScubaThrower() test_bee = ants.Bee(1) test_scuba.throw_at(test_bee) except NotImplementedError: failed_scuba += 1 finally: ants.ThrowerAnt.throw_at = old_throw_at if failed_scuba < 2: self.fail(msg="ScubaThrower is not using inheritance!")
def test_double(self): thrower = ants.ThrowerAnt() fire = ants.FireAnt() thrower_damage = ants.ThrowerAnt.damage fire_damage = ants.FireAnt.damage front = ants.ThrowerAnt() armor = 13 bee = ants.Bee(armor) self.colony.places['tunnel_0_0'].add_insect(thrower) self.colony.places['tunnel_0_1'].add_insect(fire) self.colony.places['tunnel_0_2'].add_insect(TestProblem9.queen) self.colony.places['tunnel_0_3'].add_insect(front) self.colony.places['tunnel_0_4'].add_insect(bee) TestProblem9.queen.action(self.colony) armor -= thrower_damage # Queen should always deal normal damage self.assertEqual(armor, bee.armor, "Queen damange incorrect") front.action(self.colony) armor -= thrower_damage # Front is in front, not behind self.assertEqual(armor, bee.armor, "Front damange incorrect") bee.action(self.colony) # Bee now in range of thrower thrower.action(self.colony) armor -= 2 * thrower_damage # Thrower damage doubled self.assertEqual(armor, bee.armor, "Thrower damange incorrect") TestProblem9.queen.action(self.colony) armor -= thrower_damage self.assertEqual(armor, bee.armor, "Queen damange incorrect (2)") thrower.action(self.colony) armor -= 2 * thrower_damage # Thrower damage doubled self.assertEqual(armor, bee.armor, "Thrower damange incorrect (2)") fire.place.add_insect(bee) # Teleport the bee to the fire bee.action(self.colony) armor -= 2 * fire_damage # Fire damage doubled self.assertEqual(armor, bee.armor, "Fire damange incorrect")
def test_nearest_bee_not_in_hive(self): error_msg = 'ThrowerAnt hit a Bee in the Hive' ant = ants.ThrowerAnt() self.colony.places['tunnel_0_0'].add_insect(ant) hive = self.colony.hive hive.add_insect(ants.Bee(2)) self.assertIsNone(ant.nearest_bee(hive), error_msg)
def test_die(self): bee = ants.Bee(3) self.colony.places['tunnel_0_1'].add_insect(self.queen) self.colony.places['tunnel_0_2'].add_insect(bee) self.queen.action(self.colony) self.assertFalse(len(self.colony.queen.bees) > 0, 'Game ended') bee.action(self.colony) self.assertTrue(len(self.colony.queen.bees) > 0, 'Game not ended')
def test_fire_damage(self): error_msg = 'FireAnt does the wrong amount of damage' place = self.colony.places['tunnel_0_0'] bee = ants.Bee(5) place.add_insect(bee) place.add_insect(ants.FireAnt()) bee.action(self.colony) self.assertIs(2, bee.armor, error_msg)
def test_die(self): bee = ants.Bee(3) self.colony.places['tunnel_0_1'].add_insect(TestProblem9.queen) self.colony.places['tunnel_0_2'].add_insect(bee) TestProblem9.queen.action(self.colony) self.assertIs(False, len(self.colony.queen.bees) > 0, 'Game ended') bee.action(self.colony) self.assertIs(True, len(self.colony.queen.bees) > 0, 'Game not ended')
def test_fireant_expiration(self): error_msg = "FireAnt should have, but did not expire" place = self.colony.places["tunnel_0_0"] bee = ants.Bee(1) place.add_insect(bee) ant = ants.FireAnt() place.add_insect(ant) bee.action(self.colony) self.assertEqual(ant.armor, 0, error_msg)
def test_water_deadliness_2(self): error_msg = 'Water does not kill non-watersafe Insects' test_ants = [ants.Bee(1000000), ants.HarvesterAnt(), ants.Ant(), ants.ThrowerAnt()] test_ants[0].watersafe = False #Make the bee non-watersafe test_water = ants.Water('water_TestProblemA4_0') for test_ant in test_ants: test_water.add_insect(test_ant) self.assertIsNot(test_ant, test_water.ant, msg=error_msg) self.assertIs(0, test_ant.armor, msg=error_msg)
def test_melee(self): error_msg = "ThrowerAnt doesn't attack bees on its own square." ant = ants.ThrowerAnt() self.colony.places["tunnel_0_0"].add_insect(ant) near_bee = ants.Bee(2) self.colony.places["tunnel_0_0"].add_insect(near_bee) self.assertIs(ant.nearest_bee(self.colony.hive), near_bee, error_msg) ant.action(self.colony) self.assertIs(1, near_bee.armor, error_msg)
def test_thrower(self): error_msg = 'ThrowerAnt can\'t throw from inside a bodyguard' ant = ants.ThrowerAnt() self.colony.places['tunnel_0_0'].add_insect(self.bodyguard) self.colony.places['tunnel_0_0'].add_insect(ant) bee = ants.Bee(2) self.colony.places['tunnel_0_3'].add_insect(bee) self.bodyguard.action(self.colony) self.assertIs(1, bee.armor, error_msg)
def test_ninja_deadliness(self): error_msg = 'NinjaAnt does not strike all bees in its place' test_place = self.colony.places['tunnel_0_0'] for _ in range(3): test_place.add_insect(ants.Bee(1)) ninja = ants.NinjaAnt() test_place.add_insect(ninja) ninja.action(self.colony) self.assertIs(0, len(test_place.bees), error_msg)
def test_scuba_on_land(self): place1 = self.colony.places['tunnel_0_0'] place2 = self.colony.places['tunnel_0_4'] ant = ants.ScubaThrower() bee = ants.Bee(3) place1.add_insect(ant) place2.add_insect(bee) ant.action(self.colony) self.assertIs(2, bee.armor, 'ScubaThrower doesn\'t throw on land')
def test_ninja_does_not_block(self): error_msg = 'NinjaAnt blocks bees' p0 = self.colony.places['tunnel_0_0'] p1 = self.colony.places['tunnel_0_1'] bee = ants.Bee(2) p1.add_insect(bee) p1.add_insect(ants.NinjaAnt()) bee.action(self.colony) self.assertIs(p0, bee.place, error_msg)
def test_random_shot(self): error_msg = "ThrowerAnt does not appear to choose random targets" ant = ants.ThrowerAnt() self.colony.places["tunnel_0_0"].add_insect(ant) # Place two ultra-bees to test randomness. bee = ants.Bee(1001) self.colony.places["tunnel_0_3"].add_insect(bee) self.colony.places["tunnel_0_3"].add_insect(ants.Bee(1001)) # Throw 1000 times. The first bee should take ~1000*1/2 = ~500 damage, # and have ~501 remaining. for _ in range(1000): ant.action(self.colony) # Test if damage to bee 1 is within 6 standard deviations (~95 damage) # If bees are chosen uniformly, this is true 99.9999998% of the time. def dmg_within_tolerance(): return abs(bee.armor - 501) < 95 self.assertIs(True, dmg_within_tolerance(), error_msg)
def test_non_ninja_blocks(self): error_msg = "Non-NinjaAnt does not block bees" p0 = self.colony.places["tunnel_0_0"] p1 = self.colony.places["tunnel_0_1"] bee = ants.Bee(2) p1.add_insect(bee) p1.add_insect(ants.ThrowerAnt()) bee.action(self.colony) self.assertIsNot(p0, bee.place, error_msg)
def test_scuba_on_land(self): place1 = self.colony.places["tunnel_0_0"] place2 = self.colony.places["tunnel_0_4"] ant = ants.ScubaThrower() bee = ants.Bee(3) place1.add_insect(ant) place2.add_insect(bee) ant.action(self.colony) self.assertEqual(2, bee.armor, "ScubaThrower doesn't throw on land")
def test_thrower(self): error_msg = "ThrowerAnt can't throw from inside a bodyguard" ant = ants.ThrowerAnt() self.colony.places["tunnel_0_0"].add_insect(self.bodyguard) self.colony.places["tunnel_0_0"].add_insect(ant) bee = ants.Bee(2) self.colony.places["tunnel_0_3"].add_insect(bee) self.bodyguard.action(self.colony) self.assertEqual(1, bee.armor, error_msg)