Toil and Trouble-- solvable with wrong strategy


#1

In the level Toil and Trouble, the goal is to make a targeting function that will return a specific enemy based on the type of friend submitted to the function. I attempted three strategies, some of which have the opposite outcome from which should be expected.

  • Strategy 1: all soldiers attack witch nearest to me, archers attack enemy nearest to them. Desired outcome: Success (failure acceptable) Actual outcome: Failure, most soldiers die before even reaching the witches
  • Strategy 2: all friends attack enemy nearest to them. Desired outcome: Failure. Actual Outcome: Success, about four friends remaining
  • Strategy 3: all soldiers attack witch nearest to them, archers attack any unit nearest to them. Desired outcome: Success Actual outcome: Success, about three friends remaining

I am mostly concerned with the success of Strategy 2. It seems contrary to the goals of the level, in that it does not require the player to use functions in the desired manner.


#2
this.chooseTarget =function(friend){
    if (friend == "soldier"){
        return this.findByType("witch");
        }
    else { 
        return this.findEnemies();
        
    }
};
loop {
    var friends = this.findFriends();
    for(i=0; i < friends.length; i++) {
          enemy =  friends[i].findNearest(this.chooseTarget(friends[i].type));
          this.command(friends[i], "attack", enemy);
          }
        }

This would be strategy 3 -> i get 17/20

    this.chooseTarget =function(friend){
    if (friend == "soldier"){
        return "witch";
    }
    else{
        return "enemy";
    }};
loop {
    var friends = this.findFriends();
    for(i=0; i < friends.length; i++) {
        // Use your chooseTarget function to decide what to attack.
        if(this.chooseTarget(friends[i].type) == "witch") {
          enemy =  this.findNearest(this.findByType("witch"));
        }
       else if(this.chooseTarget(friends[i].type) == "enemy") {
          enemy =  friends[i].findNearest(this.findEnemies());
        }
        this.command(friends[i], "attack", enemy);
    }
}

This should be strategy 1 -> 15/20 // imo the most logical one!

loop {
    var friends = this.findFriends();
    for(i=0; i < friends.length; i++) {
          enemy =  friends[i].findNearest(this.findEnemies());
        this.command(friends[i], "attack", enemy);
    }
}

This is strategy 2 I kill 14/20

Can anyone help me out? I also tried to use a hero with a shooting weapon, but this massively reduces the outcome. I have no idea why.

Is the mountain areas for adventurers? Or are that already finished levels?


#3

We did a re-balance of this level, try it again :).


#4

Looks good! Now I find the level only solvable with strategy 3 (6 archers and one soldier remaining).


#5

Still not working for me:

Code examples are at the top.

Is there anyway my char affects the performance?


#6

so this one is my final level to beat :slight_smile:

edit: nevermind i made it with a haste cast :slight_smile:


#7

I also failled using a kind a strategy 1.
I just ask the soldier to attack witches[0]. It seems to me more efficient to have all soldiers attacking the same witch.
But it failled totaly.
I don’t know why it’s more effective to split soldiers to attack both witches at the same time. Seems not logical to me.

I face another strange behavior. I was using this.findEnemies to have a list of target for archers. But this way, my archers were attacking only the enemies at the top of the screen. I change it to friend.findEnemies, and it worked better.
Don’t know why my hero from the top of the hill could not see all enemies.
Other remark : we still don’t know what are the functions available for our troops. I could be great to have it somewhere to know what we can use.
Last remark : the auto completion always want to add “this.” in front of the method we’re looking for, even if we wrote an element before. It finish like this:

friend.this.findEnemies();

#8

You have several things so I’m numbering them to keep them separate.

  1. soldiers vs witches
    I’d guess that has to do with witch AoE damage, with all your soldiers in one group both witches are attacking and hitting the same group of soldiers instead of hitting different groups, killing them faster. (Sometimes small difference can tip the balance from win to lose)

  2. hero vs friend vision:
    Assuming you can see everyone on the screen (which glasses?), if you are using friend.distanceTo to choose the closest target from the list then, I’d agree that it shouldn’t matter if it is your list or their list. If you aren’t using friend distanceTo then they are attacking the first one on the list that matches…

  3. code auto complete:
    The auto complete does a simple/dumb match and replace: first it matches on findEnemies and then “replaces” what you are typing with this.findEnemies() (language specific). To make the change it would need to replace check against “*.findEnemies()” and at the same time know what the default replacement is for your language “this.” if there isn’t a leading “blah.” (know that “this/self/(/etc” is replace-checked with a ‘*’ instead of the actual characters). Handle the different languages and future ones, when/if any come along.


#9

Regarding all soldiers attacking the same witch: From what I can tell each witch, if not being attacked, will heal its friend. This makes the divide and conquer strategy more important so that they won’t heal one another.


#10

wer are not silly…

for me the most logical solution would be

let all archers attack their nearest enemy and let attack soldiers the nearest enemy to you. But the best working is the opposite, anyway no solution leads to a win in my case. I had to use a heal cast tto win it ;). And i tried all solutions


#11

The rebalance seems to work. It makes the other strategies fail.

On another note, the witch’s splash damage gives me an idea for a new level with a new(?) strategy:

You have a bunch of soldiers standing in a group on one side of the field.
Your character is standing on a cliff and cannot do anything except command troops.
On the other side of the field there are a few witches (standing close together) and a shaman behind them (for high damage against single targets).
You need to command your soldiers to spread out (not move in tightly packed groups) in order to reach the enemies alive and defeat them.


#12

Ahhhhhh! Okay.

A little bit confusing that you need friend.findNearest() and friend.findEnemies() but there’s only self.findByType(), no method for my units. That’s should probably go in the Help-box when you add it.

Fun! =)


#13

Generally speaking you can see farther than your minions, so you can do the heavy sight lifting of all the different units then let them decide which ones are closest to them…


#14

I didn’t realize the wtiches were doing splash damage, thanks!

I was finally able to beat it by keeping my soldiers spread out until they got close enough to attack the witches.


#15

if you are using javascript, you can use this.findByType.call(friend,'which'); to call a hero method over the friend context.


#16

Hello everyone. I have been trying to beat this level all day. Here is my code:

Ogre Witches have some unpleasant surprises ready for you.

Define a chooseTarget function which takes a friend argument

Returns the a target to attack, depending on the type of friend.

Soldiers should attack the witches, archers should attack nearest enemy.

def ChooseTarget(friend):
enemies = self.findEnemies()
throwers = self.findByType(“thrower”)
witches = self.findByType(“witch”)
ogres = self.findByType(“ogre”)
if len(throwers) > 0:
target = friend.findNearest(throwers)
elif len(throwers) < 1 and friend.type ==“soldier”:
target = friend.findNearest(witches)
elif len(throwers) < 1 and friend.type == “archer”:
target = friend.findNearest(enemies)
return target

loop:
friends = self.findFriends()
for friend in friends:
target = ChooseTarget(friend)
self.say(“friend is” + friend +" and target is" + target)
self.command(friend, “attack”, target)


I have tried all kinds of strategies, some of which involved upwards of 50 lines of code.
Could anyone who has beaten this level give me some advice both on the code and strategy level?

Do I need to avoid the Ogres and go straight for the witches? If so, how do I keep the soldiers spread out so as to avoid splash damage?

Any help would be much appreciated!!


#17

Before you continue reading, please read the FAQ on how to properly format your code.

Don’t overthink the problem. All chooseTarget() should do is return the nearest witch to a soldier, or the nearest enemy to an archer. Not sure why you are trying to target the throwers specifically until they are all dead.

If for some reason your hero can’t see some of the enemies, then you can do this inside chooseTarget():

def chooseTarget(friend):
    enemies = friend.findEnemies() # friends have a visual range of 9001 meters
    witches = self.findByType("witch", enemies)
    # return a target!

#18

Thank you for the reply trotod. The reason I have tried so many things and made the code more complicated is that when I try this:

def ChooseTarget(friend):
       if friend.type == "soldier":
           target = friend.findNearest(witches)
       elif friend.type == "archer":
           target = friend.findNearest(enemies)
       return target
       
loop:   
    friends = self.findFriends()       
    for friend in friends:
            enemies = self.findEnemies()
            witches = self.findByType("witch", enemies)
            target = ChooseTarget(friend)
            self.say("Friend is " + friend + "and target is " + target)
            self.command(friend, "attack", target)


The top and bottom lanes cut through the throwers, then the ogres, kill the ogres but then get mowed down by the witches. So it isn’t working. I must be missing something incredibly simple but I have no idea what it is.


#19

enemies and witches should go in ChooseTarget(). (Maybe Python is different, maybe that works fine.)

Try commenting out self.say and see what happens. You can’t command during the one second it takes to say a message!


#20
def ChooseTarget(friend):
        enemies = self.findEnemies()
        witches = self.findByType("witch", enemies)
       if friend.type == "soldier":
           target = friend.findNearest(witches)
       elif friend.type == "archer":
           target = friend.findNearest(enemies)
       return target
       
loop:   
    friends = self.findFriends()       
    for friend in friends:
            target = ChooseTarget(friend)
            #self.say("Friend is " + friend + "and target is " + target)
            self.command(friend, "attack", target)

Now it is telling me that “friend” is null.

Line 10, time 0.0. Cannot read property “type” of undefined

I don’t understand why I am getting this error as I only call the function in a for loop where I am iterating over the variables I am passing to the function (friend)