IMP: parser di moltiplicazione implicita


9

A Jack piace il linguaggio di programmazione C, ma odia scrivere espressioni come V=a*b*h; moltiplicare i valori.

Vorrebbe V=abh;invece scrivere , perché il compilatore dovrebbe lamentarsi del fatto che il abhsimbolo sia indefinito poiché int a, b, h;sono definiti, in modo da poter dedurre la moltiplicazione?

Aiutalo a implementare un parser che decifra un singolo termine di moltiplicazione, a condizione che sia noto l'insieme di variabili definito nell'ambito corrente.

Per semplicità, la moltiplicazione per numero (come in 2*a*b) non viene presa in considerazione, vengono visualizzate solo le variabili.

L'input è un termine di moltiplicazione T , che soddisfa regexp:

[a-zA-Z_][a-zA-Z_0-9]*

e un set variabile Z .

Un'analisi P del termine T sull'insieme di variabili Z è una stringa che soddisfa quanto segue:

  1. dopo aver rimosso tutte le occorrenze di *da P riceviamo T,
  2. o è un nome di variabile da Z o è costituito da nomi di variabili propri da Z divisi per singoli *caratteri.

La soluzione dovrebbe stampare tutte le analisi di un termine.

Campione:

Vars           a, c, ab, bc
Term           abc
Solution       ab*c, a*bc

Vars           ab, bc
Term           abc
Solution       -

Vars           -
Term           xyz
Solution       -

Vars           xyz
Term           xyz
Solution       xyz

Vars           width, height
Term           widthheight
Solution       width*height

Vars           width, height
Term           widthheightdepth
Solution       -

Vars           aaa, a
Term           aaaa
Solution       aaa*a, a*aaa, a*a*a*a

L'input (l'elenco delle variabili e il termine) può essere fornito in qualsiasi modo adatto alla lingua.

L'output può essere in qualsiasi forma ragionevole (un analisi per riga o un elenco separato da virgole ecc.) - ma dovrebbe essere inequivocabile e possibile da leggere.

L'output vuoto è accettabile se non è possibile analizzare un termine (negli esempi ho usato '-' per chiarezza).

Questo è un codice golf, quindi vince il codice più corto.


1
Nel tuo primo esempio, credo ab*csia un'analisi errata, dal momento che cnon è una variabile consentita.
isaacg,

1
Con una scansione ricorsiva trovo esattamente il tuo risultato nel campione. Ma è discutibile: perché a*aaa aaa*ae noab*c c*ab
edc65

A causa della regola 1. dell'analisi. Sì, la moltiplicazione è solitamente commutativa, ma non andiamo così lontano - vogliamo solo "ricostruire" la moltiplicazione nell'ordine in cui è stata eseguita. In realtà nel linguaggio di Jack potremmo avere un tipo di matrice - la moltiplicazione non è quindi commutativa. E "aaaa" può essere sia giustapposizione di "aaa" e "a" o "a" e "aaa" - questo non per commutatività, piuttosto per ambiguità che stiamo prendendo in considerazione entrambi.
pawel.boczarski,

Risposte:


4

Pyth, 18 caratteri

mj\*dfqzsTsm^Qkhlz

Questa soluzione è adattata dalla mia soluzione di interpretazione dei pesci . I problemi sono in realtà molto simili.

Si aspetta input in quanto tale:

aaaa
"a", "aaa"

Fornisce un output in questo modo:

['a*aaa', 'aaa*a', 'a*a*a*a']

Provalo qui.

  • sm^Qkhlz: Genera tutte le sequenze di variabili contenenti fino alla lunghezza del numero di variabili della stringa di input.

  • fqzsT: Filtra le sequenze di variabili che corrispondono alla stringa di input

  • mj\*d: Inserisce il *simbolo e stampa.


3

Python 2 - 147 94 byte


R=lambda S,V,F=[]:S and[R(S[len(v):],V,F+[v])for v in V if v==S[:len(v)]]or print("*".join(F))

Questo definisce una funzione Rda usare come:

>>> R("abc", ["a", "bc", "ab", "c"])

Stampa l'output come:

a*bc
ab*c

1

JavaScript (ES6) 111

Adattato dalla mia risposta "pesce" , la differenza principale è trovare tutte le soluzioni, non solo la prima.

F=(v,t)=>(k=(s,r)=>s?v.map(v=>s.slice(0,l=v.length)==v&&k(s.slice(l),[...r,v])):console.log(r.join('*')))(t,[])

L'output viene stampato sulla console. Il risultato della funzione non ha significato e deve essere scartato.

Test nella console di Firefox / FireBug

F(['a','c','ab','bc'],'abc')  
a*bc  
ab*c

F(['ab','bc'],'abc')

F(['aaa','a'],'aaaa')
aaa*a
a*aaa
a*a*a*a

F(['xyz'],'xyz')
xyz
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.