Let's play some boardgame!

11

Introduction

Boardgames are a classic play between kids, but there are some kids that feel bored playing a boardgame step by step. Now they want the result to be shown before they put their hands on the board.

Challenge

Suppose this boardgame: >---#<---X---<X<--#-$

>   means the start of the game
-   means a position without danger
<   means the player should return one step back
X   means the player won't move next round
#   means a portal where the player returns to the start position
$   the first player to get there or after there wins the game

The input consists of a string with the boardgame's aspects described above and two arrays with some values (from 1 to 6) in order that both players (kid A and kid B) had got when playing one cube.

Both arrays will always have the same length >= 1.

The kid A always start the game.

You must output the kid which got the end or closer to the end first.

If neither one got the end and both kids stay at the same position print 0 or any other falsy value.

If one array runs out while the other has remaining dice rolls (due to one player missing several turns on Xs), the remaining dice rolls should be used up.

For this task, you can create a program/function, that reads input from stdin, or take parameters/arguments and output/return/print the winner kid.

Since this is , shortest answer in bytes wins!

Example Input and Output

You can also use diferrent formats of input, but you should only take the boardgame, the kid-A and the kid-B values.

Example 1:

board:  >---#<---X---<X<--#-$
kid-A:  [3,6,6,5,2,1]
kid-B:  [4,5,3,5,5,5]

output: A

Explaining:

>---#<---X---<X<--#-$     # both kids in position
B--A#<---X---<X<--#-$     # kid-A moved 3 to -
B--A#<---X---<X<--#-$     # kid-B moved 4 to # and returned home
B---#<---A---<X<--#-$     # kid-A moved 6 to X and will wait one round
B---#<---A---<X<--#-$     # kid-B moved 5 to < returned one to # and returned home
>--B#<---A---<X<--#-$     # kid-B moved 3 to -
>--B#<---X---<A<--#-$     # kid-A moved 6 to < returned one to X and will wait again
>---#<--BX---<A<--#-$     # kid-B moved 5 to -
>---#<---X--B<A<--#-$     # kid-B moved 5 to < returned one to -
>---#<---X--B<X<--#A$     # kid-A moved 5 to -
>---#<---X---<X<-B#A$     # kid-B moved 5 to -
>---#<---X---<X<-B#-$A    # kid-A moved 2 and won the game!

Example 2:

board:  >-<<<<<$
kid-A:  [1,2,3]
kid-B:  [5,5,4]

output: 0

Example 3:

board:  >-<-<#<-<-<-$
kid-A:  [5,4,2]
kid-B:  [1,1,1]

output: B

Explaining:

>-<-<#<-<-<-$     # both kids in position
>-<-<#<-<-<-$     # kid-A moved 5 to # returned home
AB<-<#<-<-<-$     # kid-B moved 1 to -
>B<A<#<-<-<-$     # kid-A moved 4 to < returned one to -
>B<A<#<-<-<-$     # kid-B moved 1 to < returned one to -
AB<-<#<-<-<-$     # kid-A moved 2 to # returned home
AB<-<#<-<-<-$     # kid-B moved 1 to < returned one to -

Current position: (A:0, B:1) output: B

removed

Posted 2016-02-10T02:10:17.330

Reputation: 2 785

Can we assume that the two arrays (for A and B) will always be the same length? – trichoplax – 2016-02-10T02:33:30.467

If one array runs out while the other has remaining dice rolls (perhaps due to one player missing several turns on Xs), should the current position be used to determine the output, or should the remaining dice rolls be used up first? – trichoplax – 2016-02-10T02:35:33.250

1@trichoplax. Yes, they will be always the same length.. I will clarify in the question – removed – 2016-02-10T02:35:40.887

1@trichoplax. The remaining dice rolls should be used up first – removed – 2016-02-10T02:36:16.600

Is example 3 correct? I run this one in my head and B never gets past space 2, while A gets to space 4. – Draco18s no longer trusts SE – 2016-02-10T17:42:33.380

@Draco18s. I've updated with an explanation – removed – 2016-02-10T17:59:31.767

Ah ha. The added explanation helps. – Draco18s no longer trusts SE – 2016-02-10T18:06:33.583

Answers

2

Perl, 188 180 + 2 = 182 bytes

Wuhuu, got to use goto.

@q=/.(?!$)/g,next if$w=$e=!@q;for(@F){a:$w+=$_;$_=$q[$w];/</?($_=-1,goto a):/X/?$e++:/#/?$w=0:!$_&&last;$e++}$r+=$"lt$r?-$w:$w;$t+=$"lt$t?-$e:$e-1}{say$w>@q?$t<0?B:A:!$r?0:$r<0?B:A

Requires -a and -E|-M5.010:

$ echo $'>-<-<#<-<-<-<-$\n5 4 2\n1 1 1' | perl -M5.010 boardgame.pl
B

Somewhat ungolfed version:

#!/usr/bin/perl -a

# Read all but last char from the board into an array
@board = /.(?!$)/g,next if $pos = $turns = !@board;
for (@F) {
    a:
    $pos+=$_;
    $_=$board[$pos];
    /</?($_=-1,goto a):
    /X/?$turns++:
    /#/?$pos=0:
    # End of Game (Victory!)
    !$_&&last;

    $turns++
}
# Make sure '$pos_diff' and '$turns_diff' are not zero by checking against [:space:]
# ' ' is less than 0 on the ascii table
$pos_diff += $"lt$pos_diff ? -$pos : $pos;
$turns_diff += $"lt$turns_diff ? -$turns : $turns-1;
}{
    say $pos>@board?
            $turns_diff<0?B
            :A
        :
        !$pos_diff?0:
        $pos_diff<0?B:
        A

andlrc

Posted 2016-02-10T02:10:17.330

Reputation: 1 613

1

Haskell, 142

_![]=fail;g!(x:y)|x>length g=Just|1<2=g!fix(\f x->case(g!!x)of;'<'->f$x-1;'X'->(0:);'#'->map$(-)(-x);_->map(+x))x y;(g?a)b=(g!)a"A"<|>(g!)b"B"

Usage:

(?) "GAME" [kidA moves] [kidB moves]

Output:

(?) ">---#<---X---<X<--#-$" [3,6,6,5,2,1] [4,5,3,5,5,5]
Just "A"

Edit:
Jikes, I golfed it to death; it fails for the last example. I'll revive it shortly.

BlackCap

Posted 2016-02-10T02:10:17.330

Reputation: 3 576

1We usually count the bytes for imports, too and I think you'll need some for fix and <|>, because they aren't in Prelude (or is there a version that includes them?). – nimi – 2016-02-10T18:47:45.430

You're right, they're not in Prelude, buuuut they are imported by default if you use lambdabot as a interpreter (I suppose counting imports are fair; I'll do that whenever I fix this) – BlackCap – 2016-02-10T19:17:35.380

1The interpreter defines the language, so you can call the language lambdabot-Haskell or similar and exclude the byte count for the imports. – nimi – 2016-02-10T20:23:27.847