Analizzatore di file obitorio DCSS


9

In questa sfida, devi analizzare i file dell'obitorio dal gioco roguelike Dungeon Crawl Stone Soup e inviarlo a STDOUT.

Cosa sono questi file dell'obitorio ??

Quando muori, viene generato un file di testo con i dati di quel personaggio all'interno. Puoi vedere quale equipaggiamento aveva il personaggio, cosa è successo negli ultimi turni e quanti mostri ha ucciso.

Puoi trovare un esempio di file obitorio qui

La sfida

Il tuo compito è creare un programma che preleva uno di quei file da STDIN, lo analizza e trasmette i dati a STDOUT.

Per rendere questa sfida un po 'più semplice, devi solo analizzare il primo blocco di testo. (fino alThe game lasted <time> (<turns> turns).

È necessario analizzare e generare le seguenti informazioni:

  • Il numero di versione
  • Il punteggio.
  • Nome, titolo, razza e classe del personaggio.
  • Il livello del personaggio.
  • La causa della morte / vittoria.
  • La quantità di giri è durata la corsa.

Esempio:

Dungeon Crawl Stone Soup version <version number> character file.

<score> <name> the <title> (level <level>, 224/224 HPs)
         Began as a <race> <class> on Mar 16, 2015.
         Was the Champion of the Shining One.
         <cause of death/victory>

         The game lasted 16:11:01 (<turns> turns).

Casi test

Caso di prova 1 - Vittoria

File di input

Esempio di output - Vittoria:

Version: 0.16.0-8-gd9ae3a8 (webtiles)
Score: 16059087
Name: Ryuzilla the Conqueror
Character: Gargoyle Berserker
Level: 27
Cause of Death/Victory: Escaped with the Orb and 15 runes on Mar 17 2015!
Turns: 97605

Caso di prova 2 - Morte

File di input

Esempio di output - Morte:

Version: 0.16-a0-3667-g690a316 (webtiles)
Score: 462
Name: 8Escape the Ruffian
Character: Bearkin Transmuter
Level: 6
Cause of Death/Victory: Slain by an orc wielding a +0 trident (3 damage) on level 4 of the Dungeon.
Turns: 3698

Regole

  • Questo è quindi vince il codice più corto.
  • In caso di pareggio, vince la risposta più vecchia.
  • Nessuna scappatoia standard.
  • L'input del file deve essere preso da STDIN
  • L'output deve essere inviato a STDOUT
  • Le etichette prima dell'output (es. Turns:) Sono opzionali.

Codice di esempio non golfato per ispirazione

Codice di generazione file obitorio in DCSS


L'output deve effettivamente contenere le etichette di riga simili Version:o è sufficiente per generare le informazioni nello stesso ordine, uno per riga?
Martin Ender,

@ MartinBüttner Le etichette sono opzionali.
DJgamer98,

La gara e la classe saranno sempre una parola ciascuna?
Martin Ender,

@ MartinBüttner Alcune razze e classi sono due parole, come Vine Stalker, Abyssal Knight e Deep Elf.
DJgamer98,

2
C'è una specifica di questo formato di file obitorio, o solo questi esempi?
Paŭlo Ebermann,

Risposte:


3

Perl, 151 byte

148 codice + 3 interruttori ( -0, -l, -p). Sono sicuro che questo può essere migliorato :)

Riceve input da STDIN e stampa il risultato alla ricezione di EOF.

perl -lp0e 's/\.{3}|\s/ /g;y/ //s;$_=join$\,(/(\d.*?).{15}\..(\d+).(.+?).\(.+?(\d+).+?\b(?:a|an) (.+?) o.+? ([^.!]+[.!])[^.!]*?(\d+)[^(]+\)..\3/)[0..2,4,3,5..7]'

Ungolfed:

use strict;
use warnings;

# set the input record separator to undef (the -0 switch)
$/=undef;
# read the text (the -l switch)
$_=<STDIN>;

# replace all '...' and spaces by a ' '
s/\.{3}|\s/ /g;
# squeeze all contiguous spaces into a single space
y/ //s;
# collect the captured groups into @p
my @p=
/(\d.*?).{15}\..      # version is the first string starting with a digit and ending 15 characters before the period
 (\d+).               # points is the next string with only digits
 (.+?).\(.+?          # name starts after a gap of one character
 (\d+).+?\b(?:a|an)\s # level is inside the next open paranthesis
 (.+?)\so.+?\s        # race, class occur after the 'a' or 'an' and end before ' o' i.e. (' on')
 ([^.!]+[.!])[^.!]*?  # cause of death is the a sentence ending with '.' or '!'
 (\d+)[^(]+\)..\3     # turns is the next sentence with digits within parantheses, followed by 2 characters and the player's name
/x;
$_=join"\n",@p[0..2,4,3,5..7]; # the level and race lines need to be swapped

# print the output (the -p switch)
print $_;

ideone.com


3

F #, 377 byte

open System.Text.RegularExpressions
let s=System.String.IsNullOrWhiteSpace>>not
let m f=Regex.Match((f+"").Split[|'\r';'\n'|]|>Seq.filter s|>Seq.take 8|>Seq.reduce(fun a z->a+z.Trim()), ".*n (.*) c.*\.([0-9]+) (.*) \(l.* (.*),.*a (.*) o.*\.(?:(S.*)|W.*(E.*)).*.T.*\((.*) .*\).").Groups|>Seq.cast<Group>|>Seq.skip 1|>Seq.map(fun z ->z.Value)|>Seq.filter s|>Seq.iter(printfn"%s")

3

Javascript (ES6), 297 230 byte

Per ora, questa è un'espressione regolare guidata dal test.

Sostituisce semplicemente le informazioni indesiderate e mantiene le cose importanti.

Crea una funzione anonima che restituisce semplicemente il testo desiderato.

_=>_.replace(/^.+version(.*) character file\.([\n\r]+)(\d+)([^\(]+) \([^\d]+( \d+),.+\n\s+.+as a(.+) on.+\n\s+(?:Was.+One\.\n)?((?:.|\n)+[!.])\n(?:.|\n)+\((\d+)(?:.|\n)+$/,'$1\n$3\n‌​$4\n$6\n$5\n$7\n$8').replace(/\s+(\.{3} ?)?/,' ')

Non è una bestia?


Grazie per il consiglio di sysreq sulle etichette che sono opzionali. Questo mi ha salvato 67 byte !


Puoi testare l'espressione resulgar su: https://regex101.com/r/zY0sQ0/1


Le etichette sono opzionali; puoi salvare parecchi byte omettendoli.
gatto

1
@sysreq The what ...?
Ismael Miguel,


2
Sto dicendo che _=>_.replace(/^.+version(.*) character file\.([\n\r]+)(\d+)([^\(]+) \([^\d]+( \d+),.+\n\s+.+as a(.+) on.+\n\s+(?:Was.+One\.\n)?((?:.|\n)+[!.])\n(?:.|\n)+\((\d+)(?:.|\n)+$/,'$1\n$3\n$4\n$6\n$5\n$7\n$8').replace(/\s+(\.{3} ?)?/,' ')è una soluzione accettabile a soli 230 byte
cat

1
@sysreq Ci scusiamo per il tempo impiegato per dire qualcosa. Ho visto il post ma ero su un tablet. Non hai idea di quanto sia doloroso fare qualcosa in un tablet. Ho sostituito il mio codice con la tua versione senza etichetta. Grazie mille per il suggerimento.
Ismael Miguel,

2

Python3, 472 byte

Ho pensato che sarei stato in grado di ottenere molto più breve. Non sorpreso, però, ho battuto la mia stessa richiesta. Eseguilo come python3 dcss.py morgue-file.txt.

import sys
n="\n"
s=" "
f=open(sys.argv[1],'r').read().split(n)[:11]
m=range
a=len
d=","
for i in m(a(f)):
 f[i]=f[i].split(s)
 for x in m(a(f[i])):
  f[i][x]=f[i][x].strip()
h=f[0]
g=f[10]
k=f[2]
def r(j,u):
 j=list(j)
 while u in j:
  j.remove(u)
 return"".join(j)
def l(x):
 c=s
 for i in m(a(x)):
  c+=x[i]+s
 return c.strip()
print(h[6]+s+h[7]+n+k[0]+n+g[0]+s+g[1]+s+g[2]+n+r(g[3],"(")+s+r(g[4],")")+n+r(k[5],d)+n+r(l(f[4])+l(f[5])+l(f[6])+l(f[7]),".")+n+r(g[17],d))

2

Vai, 589 502 489 487 byte

package main;import(."fmt";."io/ioutil";"os";."strings");func d(z,ch string)string{return Map(func(r rune)rune{if IndexRune(ch,r)<0{return r};return -1},z)};func main(){x:=Split;f,_:=ReadFile(os.Args[1]);n:="\n";l:=" ";m:=",";h:=".";q:=x(string(f),n)[:11];k:=x(q[0],l);y:=x(q[10],l);u:=x(q[2],l);g:="";for _,e:=range Fields(d(q[4],n+h)+l+d(q[5],n+h)+l+d(q[6],n+h)+l+d(q[7],n+h)){g=g+e+l};Print(k[6]+l+k[7]+n+u[0]+n+y[0]+l+y[1]+l+y[2]+n+d(y[3]+l+y[4],"()")+n+d(u[5],m)+n+g+n+d(y[17],m))}

dopo l'esecuzione go fmt, go fixed go vetecco la versione "ungolfed":

package main

import (
    . "fmt"
    . "io/ioutil"
    "os"
    . "strings"
)

func d(z, ch string) string {
    return Map(func(r rune) rune {
        if IndexRune(ch, r) < 0 {
            return r
        }
        return -1
    }, z)
}
func main() {
    x := Split
    f, _ := ReadFile(os.Args[1])
    n := "\n"
    l := " "
    m := ","
    h := "."
    q := x(string(f), n)[:11]
    k := x(q[0], l)
    y := x(q[10], l)
    u := x(q[2], l)
    g := ""
    for _, e := range Fields(d(q[4], n+h) + l + d(q[5], n+h) + l + d(q[6], n+h) + l + d(q[7], n+h)) {
        g = g + e + l
    }
    Print(k[6] + l + k[7] + n + u[0] + n + y[0] + l + y[1] + l + y[2] + n + d(y[3]+l+y[4], "()") + n + d(u[5], m) + n + g + n + d(y[17], m))
}

Modifica: l' uso di dot-imports aiuta molto.

Abbastanza autoesplicativo, ma posso spiegare se è necessario. Questo è il mio primo programma "reale" Go e sono ancora alle prime armi con Codegolf, quindi i suggerimenti sono benvenuti!

Modifica: hai detto "prendi un file da STDIN" e puoi eseguire questo script (se hai installato) eseguendo go install <foldername>e poi <binaryname> morgue-file.txtogo run main.go morgue.txt

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.