Come devo implementare un'applicazione di elaborazione dei comandi?

9

Voglio creare una semplice applicazione proof-of-concept (REPL) che accetta un numero e quindi elabora i comandi su quel numero.

Esempio: Comincio con 1. Quindi scrivo " add 2 ", mi dà 3. Quindi scrivo " multiply 7 ", mi dà 21. Poi voglio sapere se è primo, quindi scrivo " is prime "(sul numero corrente - 21), mi dà il falso. " is odd " mi darebbe la verità. E così via.

Ora, per una semplice applicazione con pochi comandi, anche un semplice switch lo farebbe per elaborare i comandi. Ma se voglio estensibilità, come avrei bisogno di implementare la funzionalità? Devo usare lo schema di comando? Costruisco un semplice parser / interprete per la lingua? Cosa succede se voglio comandi più complessi, come " multiply 5 until >200 "? Quale sarebbe un modo semplice per estenderlo (aggiungere nuovi comandi) senza ricompilare?

Modifica: per chiarire alcune cose, il mio obiettivo finale non sarebbe quello di creare qualcosa di simile a WolframAlpha, ma piuttosto un processore di lista (di numeri). Ma voglio iniziare lentamente all'inizio (su singoli numeri).

Ho in mente qualcosa di simile al modo in cui si userebbe Haskell per elaborare le liste, ma una versione molto semplice. Mi chiedo se sarebbe sufficiente qualcosa come lo schema di comando (o equivalente), o se dovessi creare un nuovo mini-linguaggio e un parser per raggiungere i miei obiettivi?

Edit2: Grazie per tutte le risposte, mi sono state di grande aiuto, ma Emmad Kareem mi ha aiutato di più, quindi la sceglierò come risposta. Grazie ancora!

    
posta Nini Michaels 07.11.2012 - 12:19
fonte

4 risposte

5

Sembra un interprete. Sembra che tu sia preoccupato dell'implementazione più della funzionalità dettagliata (sto solo indovinando qui). Questo progetto, se esteso, non è un compito banale. Assicurati di studiare chiaramente l'ambito in quanto richiede un approccio ingegneristico e non un approccio di sviluppo ad-hoc per ottenere un prodotto affidabile piuttosto che un prodotto con 1000 patch che funziona a volte solo.

Stabilisci una sintassi ed essere pronti ad analizzarlo ed eseguire i controlli di sintassi necessari. Questo collegamento può aiutarti con questo: Crea il tuo parser .

Dai un'occhiata a: questo argomento in quanto tocca diversi aspetti del lavoro, inoltre ci sono buoni collegamenti che possono aiutarti (specialmente la risposta di RMK): Creazione di un interprete di lingua . Potresti voler vedere un esempio di un progetto dall'aspetto piacevole che è in qualche modo simile a: Calcolatrice scientifica programmabile definitiva . È possibile trovare il codice sorgente e il programma di lavoro per un interprete C # a riga di comando qui riga di comando-Realizzazione-di-C # Fatto-per-didattica . Usare il compilatore per eseguire compiti complessi come l'analisi e la digitazione variabile, ecc. Può essere un modo intelligente per sfuggire alle complessità di scrivere tutto questo da soli. Inoltre, c'è l'opzione Mono che fornisce una funzione di charp shell che potresti voler dare un'occhiata a: CsharpRepl .

    
risposta data 07.11.2012 - 13:28
fonte
2

A meno che tu non sia specificamente interessato a scrivere il parser per te stesso, suggerirei di dare uno sguardo a uno dei framework del parser generator. Per C hai YACC o Bison , ma dovrebbero esserci altre alternative per altre lingue, se preferisci.

Ciò toglie la complessità di analizzare grammatiche complesse e ti consente di concentrarti sull'attività che vuoi svolgere. Ovviamente questo potrebbe essere eccessivo per la grammatica che suggerisci nella domanda, ma dal momento che hai detto di avere l'opzione di espandersi su una grammatica più complessa in seguito, vale almeno la pena di trarre ispirazione da questi framework.

    
risposta data 07.11.2012 - 14:01
fonte
2

Quello che stai descrivendo è molto vicino a una lingua dello stack .

Ad esempio in Fattore ciò che descriveresti sarebbe fatto come

1
2 +
7 *
even? not

O potresti definire le tue parole e poi usarle, come

: add ( x y -- sum ) + ;
: multiply ( x y -- product ) * ;
: odd? ( n -- ? ) even? not ;

Con queste definizioni l'esempio sopra diventa

1
2 add
7 multiply
odd?

Solitamente i linguaggi di stack sono banali da analizzare perché utilizzano singole parole separate da spazio. Ti suggerisco di dare un'occhiata a Factor: potrebbe essere proprio quello che vuoi. Dovrebbe essere facile definire le parole che fanno l'elaborazione di cui hai bisogno.

EDIT : se vuoi effettivamente progettare un linguaggio simile, ti suggerisco comunque di giocare con uno di loro. L'analisi di un linguaggio stack è banale: dividi gli spazi vuoti e un'implementazione ingenua dell'elaborazione è semplice: devi solo occuparti di ciò che accade in una pila.

    
risposta data 07.11.2012 - 17:56
fonte
1

But if I want extensibility, how would I need to implement the functionality?

Non dovresti. L'estensibilità crea un sacco di complessità con un guadagno minimo. Detto questo, dovrai fornire un gancio nello stato esistente. Un modo per vedere lo stato, modificare lo stato e fornire un meccanismo per restituire altri risultati (stampa sullo schermo). Avrai bisogno di un modo per il codice di base per scoprire i moduli, caricarli e inviare comandi a loro.

Do I use the command pattern?

Puoi, ma probabilmente non è appropriato.

Non prenderai l'intero input e lo invierai per l'elaborazione, ma invece analizzerai l'input, lo invierà al gestore corretto e lascerà che funzioni. Il comando non varia in quella comunicazione; quindi nessun modello di comando.

Do I build a simple parser/interpreter for the language?

Avrai bisogno di qualcosa per gestire l'interruzione dell'input in token. Per una soluzione estensibile, probabilmente non farai molto di più. Per una soluzione ben definita, disporre di un albero di analisi completo fornirà prestazioni migliori, gestione degli errori e capacità di debug.

but rather a list (of numbers) processor

Quindi forse dovresti esaminare la lingua LISt Processing . La giustapposizione di codice e dati dovrebbe adattarsi bene a ciò che descrivi.

    
risposta data 07.11.2012 - 17:44
fonte

Leggi altre domande sui tag