Domanda:
Linguaggio C, estrarre parole da un vettore?
Luca SSL
2013-09-15 11:33:55 UTC
Ciao ragazzi,
ho un vettore di tipo char con il seguente contenuto vettore = " Ciao! io ?? sono -- giorgio! "
Quello che dovrei fare è creare una matrice o struttura in modo da estarre SOLO le parole, cioè dovrei avere:
parola[0]= " Ciao "
parola[1]= " io "
parola[2]= " sono "
parola[3]= " giorgio "
Per parola si intende una sequenza massima per cui isalpha restituisce vero

Grazie!
Tre risposte:
BluNotte
2013-09-15 14:04:23 UTC
1) Trasforma tutto ciò che non è alfanumerico in spazio.

2) Epura gli spazi duplicati

3) Dividi la stringa sugli spazi.



http://pastebin.com/rEpKKsWL
Tizio 008
2013-09-15 23:06:19 UTC
c'è naturalmente più di un modo di farlo.

uno è usare strtok, che però puoi usare se la stringa non è un "literal" ovvero se in generale il buffer è modificabile, come specificato nella sezione Bugs del man.

In pratica la funzione è utile per estrarre dei "token" (le parole), dati dei separatori; per l'uso, cfr. sempre il man e nota che la stringa "delim" è un elenco di caratteri che consideri delimitatori; nel tuo caso, punteggiatura e spazi (spazio, tab), cioè gli passi una cosa del tipo " \t,;.:-!?" (tutti i caratteri per cui !isalpha) e qualunque altra cosa non può far parte di una "parola". Naturalmente se nel processo di estrazione un token ha lunghezza nulla, passi al successivo.

Poiché il riferimento a isalpha mi fa pensare a un esercizio diverso, quello che probabilmente devi fare è un semplice loop che scorre la stringa iniziale e memorizza ad ogni "separatore" la parola, qualcosa come (consideralo più pseudocodice che C):



for (i = 0, collecting = false, j = 0; i < strlen(s); i++) {

if (!collecting && !isalpha(s[i])) continue;

if ( isalpha(s[i]) ) { collecting = true; parola[j] = append( s[i], parola[j] ); }

else if (collecting && !isalpha(s[i])) { collecting = false; j++; }

// l'else if dovrebbe essere ridondante, ma male non dovrebbe fare....

}



alla fine j è il numero di parole trovate. Si tratta di una specie di macchina a stati. La funzione append "aggiunge" un carattere in fondo alla stringa puntata da parola[j]; la puoi fare anche intelligente nel senso che il buffer può essere creato ad hoc, p.es. in modo un po' grossolano:



char *parola[N] = NULL;



char *append(char c, char *p)

{

if (!p) { p = calloc(1, 2); if (!p) return NULL; p[0] = c; return p; }

size_t l = strlen(p);

char *r = realloc(p, l+2); // if (!r) { ...? ...}

r[l] = c; r[l+1] = 0;

return r;

}



se per la fretta non ho fatto erroracci... (nota che usare realloc per incrementare ogni volta di 1 carattere non è una idea brillante)



poi naturalmente dovrai fare tante free quante sono le "parole" inserite.
Alessio
2013-09-15 17:30:47 UTC
ciao allora io lo imposterei così:

- costruirei una matrice[ num_massimo_lettere +1 ][num_parole]

- num_parole te lo ricavi scorrendo il vettore tramite un ciclo, ogni ciclo controlla la lunghezza della parola e quando incontra un carattere che è una lettera incrementi la variabile num_parole;

- num_massimo_lettere te lo ricavi sempre durante il ciclo , metti una variabile ausiliaria num_massimo_lettere_attuali che verrà incrementata ogni volta che si incontra una lettera e verrà inizializzata a 0 quando non si incontrerà una lettera e si confronta con num_massimo_lettere.

- per mettere le lettere nella matrice, prendi e fai un altro ciclo che ti scorre il vettore, e controlli se la cella corrente contiene una lettera, nel caso in cui la contenga trasferisci la lettera, in caso contrario passi alla riga successiva ( ovviamente nel caso in cui i primi caratteri non siano lettere, imponi che non passino alla riga successiva della matrice )



puoi eseguire controlli con gli (if else) e puoi usare i cicli (while) e (for).... per i cicli ti consiglio di usare il (for) .... la matrice la dichiari dopo che ti sei ricavato num_massimo_lettere e num_parole

ciao spero di esserti stato di aiuto


Questo contenuto è stato originariamente pubblicato su Y! Answers, un sito di domande e risposte chiuso nel 2021.
Loading...