Los puntajes de tenis se encuentran con Code Golf

25

A la luz del Abierto de Australia 2014 en Melbourne, y la victoria de Stanislas Wawrinka contra Novak Djokovic, ¡propongo el siguiente desafío de código de golf!

Wawrinka y Djokovic vuelven a hacerlo en base a este CGC. Su desafío es tomar una cuerda que consta de 1 y 2 y determinar los puntajes de tenis en función del sistema de puntuación de tenis. Un "1" indica que Wawrinka ha anotado un punto, mientras que un "2" indica que Djokovic ha anotado un punto.

Por el bien de ejemplo: 1211222122111122111generará una salida de dos líneas:

Wawrinka 1 - 40
Djokovic 1 - 30

Cuanto más larga sea la cuerda, más avanzado será el puntaje.

Reglas:

  • El código más corto gana, puro y simple.
  • Los puntajes cuando se muestran deben estar alineados a la derecha y también alineados a la columna; p.ej
  • Muestra de alineación de salida:

    Wawrinka 7 5 3 -  0
    Djokovic 6 7 4 - 15
    
  • Si un juego está en progreso, la puntuación debe mostrarse después de las puntuaciones establecidas. Los puntajes del juego deben seguir los puntajes establecidos con un separador espacio-guión-espacio. Si este es el primer juego, se debe mostrar una puntuación de 0-0.

    Wawrinka 0 -  0
    Djokovic 0 - 15
    
  • Un juego irá en orden de 0, 15, 30, 40 y punto de juego. Si un juego alcanza 40-40, se declara un deuce, y el puntaje debe mostrar el deuce en la fila del jugador que anota el punto:

    Wawrinka 7 5 3 - 40
    Djokovic 6 7 4 - 40 Deuce
    
  • Si se alcanza un deuce, el siguiente punto será una ventaja para el jugador que anota el punto:

    Wawrinka 7 5 3 - Ad
    Djokovic 6 7 4 - 40
    

    El punto después de eso, si es anotado por el jugador con ventaja, gana el juego, de lo contrario el juego vuelve a decaer.

  • Si se anota más de un deuce entre puntos de ventaja, el número del deuce se indicará entre paréntesis:

    Wawrinka 7 5 3 - 40
    Djokovic 6 7 4 - 40 Deuce (2)
    
  • Se gana un set si un jugador llega a 6 juegos o más y con un margen de dos juegos en ventaja, por ejemplo, 7-5, 6-4 ... 9-7 (en el caso del quinto set de la noche anterior)

  • Los conjuntos consecutivos deben separarse con un espacio.

  • Hay desempates en el Abierto de Australia, por lo tanto, si se alcanza un set de 6-6, el primer jugador establece un desempate que alcanza siete puntos con una ventaja de margen de dos puntos. La visualización de los desempates se muestra entre corchetes de la siguiente manera:

    Wawrinka 7 6 [6]
    Djokovic 6 6 [4]
    

    Se dice que el ganador del desempate ganó el set anterior 7-6.

  • Si el quinto set llega a 6-6, el juego continúa sin tie-break hasta que se alcanza un margen de dos juegos con un jugador, siendo ese jugador el ganador de ese set. NO hay tie-breaks en el quinto set.

  • Si un jugador ha ganado tres sets, se mostrará una tercera línea que dice Wawrinka winso Djokovic winsdepende de quién ganó y el código termina.

    Wawrinka 2 6 6 3 9
    Djokovic 6 4 2 6 7
    Wawrinka wins
    
  • Si la cadena termina de tal manera que el último punto haya ganado un juego, un set o un partido, la puntuación del juego no se muestra ...

    Wawrinka 7 5 3
    Djokovic 6 7 4
    
  • Si la cadena va más allá de una partida ganada, se ignora el resto de la cadena, se muestra el puntaje y se declara el ganador.

WallyWest
fuente
3
Realmente no creo que necesitemos una nueva etiqueta llamada deportes ; El juego debería funcionar bien.
Justin
1
¿Cuál será el resultado? ¿Solo el puntaje final o cada paso en el camino?
Teun Pronk
1
@TeunPronk dependiendo de la puntuación, el partido se terminará o no. La idea parece ser: dada la cadena de puntos, cuál es el puntaje actual.
Tim Seguine
1
@McKay: no deberías poder llegar a 9-7 en el tercer set del Abierto de Australia; El desempate debe aplicarse en cada set excepto el quinto.
Chowlett
1
@WallyWest estabas en lo correcto con tu edición anterior; solo el quinto set no tiene desempate. Arreglé tu ejemplo para aclarar esto.
primo

Respuestas:

5

Perl - 424 bytes

*1=a;*2=b;@1=(Wawrinka,0);@2=(Djokovic,0);
$$_++>${$o=S^$_}&&$$_>3and$1=$2=0,
$w=$w[$_]+=($$_[$.]++>$$o[$.]||(($t=$$_[$.]==$$o[$.])&&!$%&&$.<5))&&
$$_[$.]>5+$%&&!($1[$.]=$2[$.+=!$%]=$w<2&&0,$$_[$.-1]+=$%,$%=$t)for<>=~/./g;
@s=(' 0',15,30,(40)x($e=$$o<3||$$o-2),Ad);
$%and$_="[$_]"for@1[-1],@2[-1];$d[$&]=$1>2&&$1==$2&&' Deuce'.($1>3&&" ($e)");
print"@1",$w<3&&" - $s[$1]$d[1]","\n@2",$w<3&&" - $s[$2]$d[2]",$w>2&&"\n${$&}[0] wins"

Saltos de línea se han añadido para mejorar la legibilidad cordura horizontal.

Creo que esta es una solución completa, según la puntuación del Abierto de Australia :

  • Lo mejor de cinco sets (también conocido como carrera a tres).
  • Los sets 1-4 se juegan como un desempate 6-6.
  • El conjunto 5 se juega como un conjunto de ventaja.

Casos de prueba


1211222122111122111

Wawrinka 1 - 40
Djokovic 1 - 30

12112221221111221112

Wawrinka 1 - 40
Djokovic 1 - 40 Deuce

121122212211112211122

Wawrinka 1 - 40
Djokovic 1 - Ad

1211222122111122111221

Wawrinka 1 - 40 Deuce (2)
Djokovic 1 - 40

22111111212122221122111212212112121221212211221121222222112112221121121122221122221211111222121222122211212122111212112211222121211212211212211122121211112222222212211121122

Wawrinka 6 [5] - 30
Djokovic 6 [6] - 40

221111112121222211221112122121121212212122112211212222221121122211211211222211222212111112221212221222112121221112121122112221212112122112122111221212111122222222122111211222

Wawrinka 6 0 -  0
Djokovic 7 0 -  0

1122222211121211121211111121111211221222212212112221211222211222112212211121122122212122212222122212212211221111121222111221211111211112222212122122112111212121221221212211112122212211111111112111212222221112212121122212121111122111222222111212221121221111222122122222111212111111221121122111122122111222222121122221112221221122221121211212111122111121212112112121222122

Wawrinka 5 4 6 6 5 - 15
Djokovic 7 6 4 4 6 - 40

11222222111212111212111111211112112212222122121122212112222112221122122111211221222121222122221222122122112211111212221112212111112111122222121221221121112121212212212122111121222122111111111121112122222211122121211222121211111221112222221112122211212211112221221222221112121111112211211221111221221112222221211222211122212211222211212112121111221111212121121121212221222

Wawrinka 5 4 6 6 5
Djokovic 7 6 4 4 7
Djokovic wins

222221112112212212222111222211111111121111121112211221221211212121122211222112111112122122212222211112122212221111121111121211212112112112221221121122121121112221221222122122211222212121212112112111221221121112222212122222221111112222222221221122211221121111221121222222111111122221122111211121222112112122212122221121222221222121212111121221221112111212212222122212212212112111112112112121112221111221221221121222122211221212211111111222222121221112221212

Wawrinka 6 7 6 4 7 - 40
Djokovic 3 5 7 6 8 - Ad

2222211121122122122221112222111111111211111211122112212212112121211222112221121111121221222122222111121222122211111211111212112121121121122212211211221211211122212212221221222112222121212121121121112212211211122222121222222211111122222222212211222112211211112211212222221111111222211221112111212221121121222121222211212222212221212121111212212211121112122122221222122122121121111121121121211122211112212212211212221222112212122111111112222221212211122212122

Wawrinka 6 7 6 4 7 
Djokovic 3 5 7 6 9 
Djokovic wins

Todos los puntajes intermedios para el último caso de prueba se pueden ver aquí: http://codepad.org/FzDIcf0W

primo
fuente
¿No se supone que 11-9 solo es válido como un quinto set?
Volatilidad
@Volatility en realidad, tenías razón. Necesitaré actualizar
primo
2

ECMAScript 6 - 635 caracteres

f=(p,q,C)=>{B='';T=' ';L=(x)=>(B+x).length;M=(x,y)=>x>y?x:y;E=(a)=>{var x=L(a[0]),y=L(a[1]),q=M(x,y);for(;x++<q;)a[0]=T+a[0];for(;y++<q;)a[1]=T+a[1]};E(a=[p,q]);g=[m=n=o=i=t=z=0,0];s=[0,0];S=[0,0];w=2;O=(i)=>a[i]+(n+o>0?T+s[i]:B)+(o>0?(t?' ['+g[i]+']':' - '+[' 0',15,30,40,'Ad'][g[i]]+(z>0&&g[0]+g[1]==6&&i==w?' Deuce'+(z>1?' ('+z+')':B):B)):B)+'\n';while(W=C[i++]){w=--W;++o;if((d=++g[w])>M(t?6:3,(e=g[l=1-w])+1)){g=[o=z=0,0];j=++s[w];k=s[l];t=++n>11;if(j>M(5,m>4||k<6?k+1:6)){E(s);a[0]+=T+s[0];a[1]+=T+s[1];s=[n=0,0];++m;if(++S[w]>2)break}}else if(!t&&d+e>7){--g[w];--g[l];++z}}E(s);E(g);return O(0)+O(1)+(S[w]>2?(w?q:p)+' wins':B)}

Con comentarios:

// Function f takes arguments:
//   p - Player 1 name
//   q - Player 2 name
//   C - String of 1s and 2s representing points won by players.
f=(p,q,C)=>{
    /* Empty String          */ B='';
    /* Space                 */ T=' ';
    /* String Length Func.   */ L=(x)=>(B+x).length;
    /* Max Function          */ M=(x,y)=>x>y?x:y;
    /* Equalize Length Func. */ E=(a)=>{var x=L(a[0]),y=L(a[1]),q=M(x,y);for(;x++<q;)a[0]=T+a[0];for(;y++<q;)a[1]=T+a[1]};
    /* No. of sets           */ m=0;
    /* No. games in set      */ n=0;
    /* No. points in game    */ o=0;
    /* Input Index           */ i=0;
    /* Output String         */ E(a=[p,q]);
    /* Current Game's Points */ g=[0,0];
    /* Current Set's Games   */ s=[0,0];
    /* No. sets won          */ S=[0,0];
    /* Is a tiebreaker       */ t=0;
    /* No. of deuces         */ z=0;
    /* Current match result  */ w=2;
    /* Output Fnctn  */ O=(i)=>a[i]+(n+o>0?T+s[i]:B)+(o>0?(t?' ['+g[i]+']':' - '+[' 0',15,30,40,'Ad'][g[i]]+(z>0&&g[0]+g[1]==6&&i==w?' Deuce'+(z>1?' ('+z+')':B):B)):B)+'\n';
    while(W=C[i++]){
        w=--W;
        // w - index of winner of current game
        // l - index of loser of current game
        // d - winner of current point's game score
        // e - loser of current point's game score
        ++o;
        if((d=++g[w])>M(t?6:3,(e=g[l=1-w])+1)){ 
            g=[0,0];  // Reset the game score.
            o=z=0;
            j=++s[w]; // j = Increment the winner's set score
            k=s[l];   // k = Loser's set score
            t=++n>11; // Is a tiebreak?
            if(j>M(5,m>4||k<6?k+1:6)){
                E(s);
                a[0]+=T+s[0]; // Add to output
                a[1]+=T+s[1]; // Add to output
                s=[n=0,0];  // Reset current set's no. of games & no. of deuces.
                ++m;        // Increment no. of sets.
                if(++S[w]>2)break;     // Increment winners no. sets won and check if match won.
            }
        }
        else if(!t&&d+e>7){--g[w];--g[l];++z}// Check if deuces increased.
    }
    E(s); // Format sets strings.
    E(g); // Format games strings.
    return O(0)+O(1)+(S[w]>2?(w?q:p)+' wins':B);
}

Pruebas

var tests=[
            '',
            '1',
            '2',
            '11',
            '222',
            '1111',
            '2222',
            '1112221',
            '11122212',
            '121212121',
            '1212121212',
            '1211222122111122111',
            '12112221221111221112',
            '121122212211112211122',
            '1211222122111122111221',
            '1111222211112222111122221111222211112222111122221212121212121212121',
            '11111111111111111111111111111111111111111111111111111111111111111111111',
            '111111111111111111111111111111111111111111111111111111111111111111111111',
            '1111111111111111111111111111111111111111111111111111111111111111111111111'
        ];
for(var ex in tests) console.log('Test '+ex+'\n'+tests[ex]+'\n'+f('Wawrinka','Djokovic',tests[ex]));

Salidas de prueba

Test 0

Wawrinka
Djokovic


Test 1
1
Wawrinka 0 - 15
Djokovic 0 -  0


Test 2
2
Wawrinka 0 -  0
Djokovic 0 - 15


Test 3
11
Wawrinka 0 - 30
Djokovic 0 -  0


Test 4
222
Wawrinka 0 -  0
Djokovic 0 - 40


Test 5
1111
Wawrinka 1
Djokovic 0


Test 6
2222
Wawrinka 0
Djokovic 1


Test 7
1112221
Wawrinka 0 - Ad
Djokovic 0 - 40


Test 8
11122212
Wawrinka 0 - 40
Djokovic 0 - 40 Deuce


Test 9
121212121
Wawrinka 0 - Ad
Djokovic 0 - 40


Test 10
1212121212
Wawrinka 0 - 40
Djokovic 0 - 40 Deuce (2)


Test 11
1211222122111122111
Wawrinka 1 - 40
Djokovic 1 - 30


Test 12
12112221221111221112
Wawrinka 1 - 40
Djokovic 1 - 40


Test 13
121122212211112211122
Wawrinka 1 - 40
Djokovic 1 - Ad

Test 14
1211222122111122111221
Wawrinka 1 - 40 Deuce
Djokovic 1 - 40


Test 15
1111222211112222111122221111222211112222111122221212121212121212121
Wawrinka 6 [10]
Djokovic 6 [ 9]


Test 16
11111111111111111111111111111111111111111111111111111111111111111111111
Wawrinka 6 6 5 - 40
Djokovic 0 0 0 -  0


Test 17
111111111111111111111111111111111111111111111111111111111111111111111111
Wawrinka 6 6 6
Djokovic 0 0 0
Wawrinka wins

Test 18
1111111111111111111111111111111111111111111111111111111111111111111111111
Wawrinka 6 6 6
Djokovic 0 0 0
Wawrinka wins
MT0
fuente
1

Javascript - 743 bytes

var b=process.argv[2],c=[0,0],e=[],g=[0,0],h=[0,0],k=["0","15","30","40"],l=["Wawrinka","Djokovic"];function m(a){var d="",f;for(f in e)d+=e[f][a]+" ";3<=c[0]||3<=c[1]||(d+=g[a]+" - ",f=h[a],a=h[(a+1)%2],d=n()?d+("["+f+"]"):3>f||3>a?d+k[f]:f>a?d+"Ad":d+k[3]);return d}function n(){return 6<=g[0]&&6<=g[1]}function p(){var a=q;g[a]++;h=[0,0];7<=g[a]?(e.push(g),g=[0,0],c[a]++):6<=g[a]&&g[a]>g[(a+1)%2]+1&&(e.push(g),g=[0,0],c[a]++)} for(var r in b){var q=parseInt(b[r])-1,s=++h[q];n()?7<=s&&(4>e.length?p():s>h[(q+1)%2]+1&&p()):4<=s&&s>h[(q+1)%2]+1&&p()}console.log(l[0]," ",m(0));console.log(l[1]," ",m(1),n()?"":2<h[0]&&2<h[1]&&h[0]==h[1]?"Deuce"+(3<h[0]?" ("+(h[0]-2)+")":""):"");console.log(3<=c[0]||3<=c[1]?(3<=c[0]?l[0]:l[1])+" wins":"");

Sin compilador de cierre:

var input = process.argv[2];

var score = [0,0];
var match = [];
var set = [0,0];
var game = [0,0];
var gameScore = [ '0', '15', '30', '40' ];
var names = ['Wawrinka', 'Djokovic'];

function printScores(who)
{
    var out = '';
    for (var i in match) {
        out += match[i][who] + ' ';
    }

    if (!isDone()) {
        out += set[who] + ' - ';

        var point = game[who], otherPoint = game[(who+1)%2];

        if (isTieBreaker()) { // Tie breaker
            out += '['+point+']';
        } else {
            if (point < 3 || otherPoint < 3) {
                out += gameScore[point];
            } else if (point > otherPoint) {
                out += 'Ad';
            } else {
                out+= gameScore[3];
            }
        }
    }

    return out;
}

function printDeuce()
{
    if (isTieBreaker()) {
        return '';
    } else {
        return (game[0] > 2 && game[1] > 2 && game[0] == game[1]) ? ('Deuce' + (game[0] > 3 ? ' (' + (game[0] - 2) + ')' : '')) : '';
    }

}

function isDone()
{
    return score[0] >= 3 || score[1] >= 3;
}

function isTieBreaker()
{
    return set[0] >= 6 && set[1] >= 6;
}

function getOther(who)
{
    return (who + 1) % 2;
}

function addPoint(who)
{
    var points = ++game[who];

    if (isTieBreaker()) {
        if (points >= 7) {
            if (match.length < 4) {
                addGame(who);
            } else if (points > (game[getOther(who)]+ 1)) {
                addGame(who);
            }
        }
    } else {
        if (points >= 4 && points > (game[getOther(who)] + 1)) {
            addGame(who);
        }
    }
}

function addGame(who)
{
    set[who]++;
    game = [0,0];

    if (set[who] >= 7) { // Won Tiebreaker
        addSet(who);
    } else if (set[who] >= 6 && set[who] > (set[getOther(who)] + 1)) {
        addSet(who);
    }
}

function addSet(who)
{
    match.push(set);
    set = [0,0];
    score[who]++;
}

// Play game
for(var i in input) {
    addPoint(parseInt(input[i]) - 1);
}

console.log(names[0], ' ', printScores(0));
console.log(names[1], ' ', printScores(1), printDeuce());
console.log(isDone() ? ((score[0] >= 3 ? names[0] : names[1]) + ' wins') : '');
Populus
fuente