2012-10-31 2 views
9

Attualmente sto progettando un'applicazione di C++ linux. Sarà eseguito dalla riga di comando, poi una volta in esecuzione ho bisogno di essere in grado di emettere comandi per controllare la sua esecuzione, idealmente qualcosa di simile al seguente:Interfaccia della riga di comando C++

$ sudo ./myapplication 
APP > 
APP > 
APP > //just pressing return 
APP > openlog test1.txt //APP will now call the openlog function 
APP > 

immagino che questo è un compito relativamente semplice, ma ho non ho idea di quale sarebbe stata chiamata una tale interfaccia per cercarne una. Qualcuno sa di una biblioteca o di un esempio che può eseguire questa funzione? O devo scrivere il mio utilizzando cout e cin? In tal caso, ci sarebbe un approccio preferito?

+1

C++ non ha riflessione. Dovrai lavorare su questo. – chris

+0

Se non sai come fare, non dovresti scrivere applicazioni che devono essere eseguite da superuser .... – Barmar

+3

@Barmar È iperbolico dire che questa applicazione deve essere eseguita da su, e più difficile dirlo a qualcuno non dovrebbe scrivere applicazioni gestite da superutente a causa di un livello percepito di esperienza. –

risposta

13

Raccomando la libreria GNU readline per questo. Si prende cura del noioso lavoro di ottenere linee di input e permette all'utente di modificare la sua linea con backspace, frecce sinistra e destra, ecc, e di richiamare il comando precedente usando la freccia su e anche cercare il comando più vecchio usando^R, ecc. Readline viene installato con tipiche distribuzioni unix-like come linux, ma se non ce l'hai, puoi trovarlo here.

Edit: Ecco un esempio minimo readline:

#include <stdio.h> 
#include <readline/readline.h> 
#include <readline/history.h> 

int main(int argc, char ** argv) 
{ 
    while(1) 
    { 
     char * line = readline("> "); 
     if(!line) break; 
     if(*line) add_history(line); 
     /* Do something with the line here */ 
     free(line); 
    } 
} 
-4

È possibile scrivere l'applicazione come applicazione TCL o Python e utilizzarli come front-end.

1

È necessario eseguire almeno parzialmente il rollover. GNU readline potrebbe essere in grado di aiutare leggermente; controlla http://en.wikipedia.org/wiki/GNU_readline per un programma breve che è lo "scheletro" che raggiunge questo e attorno al quale puoi effettivamente aggiungere il codice.

1

Probabilmente dovresti dare un'occhiata a the readline library. Ha un po 'di una curva di apprendimento, ma è ancora molto più facile che ricreare una CLI completa da soli. Controlla la licenza anche se potrebbe non essere appropriata per il tuo progetto.

5

La biblioteca GNU readline è grande se si vuole piena funzionalità della linea di editing e di storia, ma se un semplice sufficiente un prompt (o se non si vuole la licenza GNU), allora si può fare questo con solo la libreria standard:

#include <iostream> 
#include <string> 

void process(std::string const & line); 

int main() 
{ 
    for (std::string line; std::cout << "APP > " && std::getline(std::cin, line);) 
    { 
     if (!line.empty()) { process(line); } 
    } 

    std::cout << "Goodbye.\n"; 
} 
2

sono d'accordo con il commento di Chris che questo sarà più difficile in una lingua che non è riflettente. In C++, dovrai mappare in modo esplicito tutto ciò che scrivi su una funzione specifica.

Se avete intenzione di rotolare il proprio, il vostro disegno generale dovrebbe essere simile a questa:

  • Leggi linea di ingresso (molto probabilmente utilizzando cin.getline in una stringa)
  • Identificare la prima parola e determinare se esegue il mapping a qualsiasi funzione (ad esempio, è possibile utilizzare una semplice istruzione switch, tabella hash, ecc.)
  • Se non si associa a una funzione, registrare un errore e ristampare il prompt.
  • Se si esegue il mapping, è necessario esaminare le altre parole nella riga.
  • Per ogni altra parola, è necessario convertire la stringa in qualsiasi tipo di dati desiderato come parametri di funzione parola per parola (le stringhe di stringhe saranno utili qui).
  • Ora devi assicurarti che i parametri che hai fornito siano legittimi per la funzione che hai chiamato. Puoi pre-controllarli prima di chiamare la funzione, o controllare gli errori all'interno della funzione.
  • Una volta verificato il nome della funzione e i parametri sono corretti (e del numero giusto) è possibile chiamare la funzione.

In un linguaggio riflessivo, la prima metà è molto più semplice in quanto è possibile convertire una stringa direttamente in un nome di funzione.

+1

Consiglio vivamente 'std :: getline' su' std :: istream :: getline'. – chris

2

GNU readline è di gran lunga una scelta eccellente, come altri hanno suggerito. Se i problemi di licenza ti obbligherebbero a escluderlo, allora dovresti considerare linenoise.

+0

Sembra che linenoise fornisca anche la funzione di completamento, che potrebbe essere ottima. – etham

1

essere consapevoli della licenza GPL di GNU Readline. Nelle risposte, la gente ha parlato della licenza GPL di GNU readline. In questa risposta, vorrei sottolineare le implicazioni della licenza GPL, che i nuovi utenti/sviluppatori potrebbero trascurare.

testo copiato da https://en.wikipedia.org/wiki/GNU_Readline

Scelta del GPL come licenza di GNU Readline [modifica] GNU Readline è noto per essere una libreria software gratuito che è rilasciato sotto la GNU General Public License (GPL), invece di GNU Lesser General Licenza pubblica (LGPL). Le librerie software libere sono spesso concesse in licenza sotto LGPL, ad esempio, GNU C Library, GNU gettext e FLTK.

Uno sviluppatore di un'applicazione che sceglie di collegarsi ad un LGPL licenza libreria quando la costruzione di una nuova applicazione è necessario avere la libreria con licenza LGPL che utilizza rimanere sotto la LGPL durante la distribuzione l'applicazione risultante combinato. La parte dell'applicazione combinata esclusa la libreria con licenza LGPL può rimanere sotto la licenza originale . [1] Ciò è in contrasto con uno sviluppatore che sceglie di utilizzare una libreria con licenza GPL per creare una nuova applicazione, nel qual caso l'intera applicazione risultante deve ottenere la licenza sotto licenza GPL quando è distribuita, per conformarsi alla sezione 5 dello GPL. [2] [3]

Implicazioni della GNU Readline licenza GPL [modifica] Un esempio importante di una domanda di cambiare la sua licenza di rispettare il copyleft condizioni di GNU Readline è CLISP, un'implementazione di Common Lisp. Originariamente pubblicato nel 1987, ha cambiato la licenza GPL nel 1992, [4] dopo uno scambio di email tra uno degli autori originali di CLISP, Bruno Haible e Richard Stallman, in cui Stallman ha sostenuto [5] che il collegamento readline in CLISP significava che Haible era obbligata a ri-licenziare CLISP sotto la GPL se desiderava distribuire l'implementazione di CLISP che usava readline. [6]

alternativi librerie di editing della linea di comando che sono permissively concessi in licenza possono essere utilizzati da progetti di software che vogliono implementare funzionalità di editing linea di di comando, ma desiderano restare sotto una licenza permissiva . Tipico tra questi è il libedit con licenza BSD. Alcune applicazioni, come MariaDB [7] o PHP [8], consentono all'utente di selezionare al momento della compilazione se effettuare il collegamento con GNU Readline o con il libedit . Altre librerie di modifica della riga di comando hanno un duplice scopo: hanno API che allineano quelle di alcuni progetti principali e hanno i termini di licenza compatibili con . Un esempio di ciò è la libreria Haskeline, che espone un'API Haskell compatibile sia al Compilatore Glasgow Haskell [9] sia ad altri progetti Haskell che necessitano di servizi di modifica riga . [10]

I collegamenti a diverse librerie di questo tipo sono elencati nei collegamenti esterni.