Torna indietro   Hardware Upgrade Forum > Software > Programmazione

Ecovacs Goat O1200 LiDAR Pro: la prova del robot tagliaerba con tagliabordi integrato
Ecovacs Goat O1200 LiDAR Pro: la prova del robot tagliaerba con tagliabordi integrato
Nuova frontiera per i robot tagliaerba, con Ecovacs GOAT O1200 LiDAR Pro che riconosce l'ambiente in maniera perfetta, grazie a due sensori LiDAR, e dopo la falciatura può anche rifinire il bordo con il tagliabordi a filo integrato
Recensione Samsung Galaxy S26+: sfida l'Ultra, ma ha senso di esistere?
Recensione Samsung Galaxy S26+: sfida l'Ultra, ma ha senso di esistere?
Equilibrio e potenza definiscono il Samsung Galaxy S26+, un flagship che sfida la variante Ultra e la fascia alta del mercato con il primo processore mobile a 2nm. Pur mantenendo l'hardware fotografico precedente, lo smartphone brilla per un display QHD+ da 6,7 pollici d'eccellenza, privo però del trattamento antiriflesso dell'Ultra, e per prestazioni molto elevate. Completano il quadro la ricarica wireless a 20W e, soprattutto, un supporto software settennale
Zeekr X e 7X provate: prezzi, autonomia fino a 615 km e ricarica in 13 minuti
Zeekr X e 7X provate: prezzi, autonomia fino a 615 km e ricarica in 13 minuti
Zeekr sbarca ufficialmente in Italia con tre modelli elettrici premium, X, 7X e 001, distribuiti da Jameel Motors su una rete di 52 punti vendita già attivi. La Zeekr X parte da 39.900 euro, la 7X da 54.100: piattaforma a 800V, chip Snapdragon di ultima generazione, ricarica ultraveloce e un'autonomia dichiarata fino a 615 km WLTP. Le prime consegne sono previste a metà aprile
Tutti gli articoli Tutte le news

Vai al Forum
Rispondi
 
Strumenti
Old 10-08-2009, 21:34   #1
Y3PP4
Member
 
Iscritto dal: Jul 2009
Messaggi: 210
[C] Problema ciclo for dentro un ciclo while

Giorno,

sto facendo delle prove scrivendo un piccolo parser (niente di chè, solo escape di stringhe).
Attualmente ho messo a punto un algoritmo semplice semplice che prevede tramite un
while(!feof( fp )) la chiamata a varie funzioni, una delle quali è fgets.
Ottenuta la stringa poi passo tutto a un'altra funzione che tramite un ciclo for così definito:
Codice:
for( i=0; i<strlen( line ); i++ )
richiama continuamente uno switch(line[i]) e in seguito testa: se il carattere non è una tabulazione o spazio lo salva in un'altro puntatore e al termine del ciclo for ritorna la stringa.

Qui sorge il problema. Se provo a stampare le varie stringhe ottengo tutto con successo, ma ahimè l'ultima linea mi viene stampata due volte.

Qualcuno sà da cosa possa dipendere il problema?

Di seguito posto il problema semplificato (per non complicare le cose):
Codice:
// importo gli header necessari
void cleanString( char *line, char *escapedLine );
int main()
{
    // ... fp è argv[1]
    char line[500];
    char *escapedLine;
    while( !feof( fp ) )
    {
        fgets( line, sizeof( line ), fp );
       // alloco la memoria
        escapedLine = malloc ( strlen( line ) + 1 ) * ( sizeof( char ) ) );
        cleanString( line, escapedLine ); // 
        printf("%s\n", escapedLine);
        free( escapedLine );
    }
    return( EXIT_SUCCESS );
}
void
cleanString( char *line, char *escapedLine )
{
    unsigned int i;
    unsigned int a = 0; //  counter per cleanLine
    for( i=0; i<strlen( line ); i++ )
    {
        switch( line[i] )
        {
            case ' ' :
            case '\t':
            case '\n':
                break;
            default:
                cleanLine[a] = line[i];
                a++;
                break;
        }
    }
    return;
}
Questo è quanto.
Supponendo di avere un file con semplici frasi come potrebbe essere:
Giorno a tutti,
oggi mi sento
bene.

Ottengo come risultato:
Giornoatutti,
oggimisento
bene.
bene. <-- ripetuto due volte!

Grazie a tutti, buona notte.

Ultima modifica di Y3PP4 : 10-08-2009 alle 21:37.
Y3PP4 è offline   Rispondi citando il messaggio o parte di esso
Old 10-08-2009, 22:54   #2
DanieleC88
Senior Member
 
L'Avatar di DanieleC88
 
Iscritto dal: Jun 2002
Città: Dublin
Messaggi: 5989
Imposta il primo carattere della stringa a '\0' prima di leggere con fgets(), visto che è un buffer statico, dovrebbe bastare.

ciao
__________________

C'ho certi cazzi Mafa' che manco tu che sei pratica li hai visti mai!
DanieleC88 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 00:15   #3
Y3PP4
Member
 
Iscritto dal: Jul 2009
Messaggi: 210
Grazie mille per la risposta

Il sistema funziona (mi stampa solo un'ultima riga bianca ma dato che non dovrò stamparlo ed è un carattere nullo non dovrei avere problemi col parser...)

Come mai bisogna usare questo escape (o hack che dir si voglia) ?
Io avevo esplicitamente detto:
"mentre non incontri la fine del file -> leggi una riga -> leggi ogni carattere della riga -> se non è uno spazio mettilo da parte -> ritornami tutti i caratteri messi da parte -> stampa i caratteri ritornati"

Esegue palesemente un ciclo in più (in cui mi pare di capire che la stringa rimane inalterata) di quello richiesto...
inoltre perchè la stringa rimane immutata? non è dichiarata come static...

chiedo scusa ma alla solita se è possibile vorrei chiarire il concetto

Buona notte e mille grazie ancora!
Y3PP4 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 00:48   #4
nuovoUtente86
Senior Member
 
Iscritto dal: Mar 2007
Messaggi: 7863
effettua una prima fgets fuori dal while e posiziona la chiamata come ultima istruzione del while in modo da sincronizzare con feof la posizione sullo stream.
nuovoUtente86 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 07:12   #5
DanieleC88
Senior Member
 
L'Avatar di DanieleC88
 
Iscritto dal: Jun 2002
Città: Dublin
Messaggi: 5989
Quote:
Originariamente inviato da Y3PP4 Guarda i messaggi
Esegue palesemente un ciclo in più (in cui mi pare di capire che la stringa rimane inalterata) di quello richiesto...
inoltre perchè la stringa rimane immutata? non è dichiarata come static...
Perché finché non "fallisce" per la prima volta la fgets() non ti viene dato l'EOF, quindi l'ultimo ciclo sarà quello in cui la fgets() non avrà più niente da leggere. Il problema era che il tuo buffer era un'array dichiarata come variabile locale, che nasce e muore con la funzione in cui è stata dichiarata: al termine di ogni ciclo, i vecchi contenuti non vengono cancellati (al limite devi terminare tu a mano la stringa, come ti ho consigliato di fare io), e quindi nell'ultimo ciclo prima dell'EOF ottieni comunque la riga che già era dentro il buffer.
Alternativamente, puoi fare come consiglia nuovoUtente86 ed ottenere lo stesso effetto.

ciao
__________________

C'ho certi cazzi Mafa' che manco tu che sei pratica li hai visti mai!
DanieleC88 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 21:26   #6
Y3PP4
Member
 
Iscritto dal: Jul 2009
Messaggi: 210
Anzitutto mille grazie ad entrambi per la risposta.
Mille grazie nuovoUtente86 per il suggerimento, adesso che me lo hai esposto, tra l'altro, sembra la soluzione ad hoc al problema, mi sarà molto utile : grazie mille!

Quote:
Originariamente inviato da DanieleC88 Guarda i messaggi
Perché finché non "fallisce" per la prima volta la fgets() non ti viene dato l'EOF, quindi l'ultimo ciclo sarà quello in cui la fgets() non avrà più niente da leggere. Il problema era che il tuo buffer era un'array dichiarata come variabile locale, che nasce e muore con la funzione in cui è stata dichiarata: al termine di ogni ciclo, i vecchi contenuti non vengono cancellati (al limite devi terminare tu a mano la stringa, come ti ho consigliato di fare io), e quindi nell'ultimo ciclo prima dell'EOF ottieni comunque la riga che già era dentro il buffer.
ciao
Ancora una volta mi hai illuminato con una esposizione chiarissima: ti sono (nuovamente) debitore! Adesso mi è tutto chiaro;
soprattutto perchè dare il fine stringa al primo carattere prima dello fgets.
Grazie mille (inoltre mi sono chiarito anche il fatto che feof "cattura" un eof settato da un'altra funzione e non lo setta da solo).

Buona serata a tutti :-).
Y3PP4 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 22:07   #7
Y3PP4
Member
 
Iscritto dal: Jul 2009
Messaggi: 210
Uh, un'ultima cosa che mi era sfuggita.
Io dealloco la memoria con free(fp)... se libero la memoria contenente la stringa come fà ancora a restare in memoria nel ciclo successivo?

Solo una piccola curiosità



Buona serata,
ciao.
Y3PP4 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 22:46   #8
DanieleC88
Senior Member
 
L'Avatar di DanieleC88
 
Iscritto dal: Jun 2002
Città: Dublin
Messaggi: 5989
Perché la prendi da line e ce la ricopi dentro (la fgets() opera sulla line allocata staticamente, non sulla escapedString allocata dinamicamente).

ciao
__________________

C'ho certi cazzi Mafa' che manco tu che sei pratica li hai visti mai!
DanieleC88 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 23:00   #9
Y3PP4
Member
 
Iscritto dal: Jul 2009
Messaggi: 210
Quote:
Originariamente inviato da DanieleC88 Guarda i messaggi
Perché la prendi da line e ce la ricopi dentro (la fgets() opera sulla line allocata staticamente, non sulla escapedString allocata dinamicamente).

ciao
....

non ho parole: se mi scordo pure come funzionano gli algoritmi più semplici che scrivo pochi giorni prima, sarà meglio che ricorra ad una cura di fosforo.
Il fatto (a mia giustificazione ) è che nel programma uso un puntatore ad una sequenza di comandi (dichiarati come puntatori a funzione) per usare anzichè ad esempio fgets(...);
parser->getLine(...);

Beh che dire, dopo questa "svista" sarà meglio che con il prossimo post possa recuperare credito nel forum , magari chiedendo(ti) consiglio (o aiuto) su un algoritmo, quantomeno brillante.

Buona notte . (a mia giustificazione posso chiamare anche in causa l'ora? e la giornata in piscina?)
Y3PP4 è offline   Rispondi citando il messaggio o parte di esso
Old 11-08-2009, 23:07   #10
DanieleC88
Senior Member
 
L'Avatar di DanieleC88
 
Iscritto dal: Jun 2002
Città: Dublin
Messaggi: 5989
Lascia stare, non servono giustificazioni... c'è chi (io per primo) ha fatto e fa cose ben peggiori.

ciao
__________________

C'ho certi cazzi Mafa' che manco tu che sei pratica li hai visti mai!
DanieleC88 è offline   Rispondi citando il messaggio o parte di esso
 Rispondi


Ecovacs Goat O1200 LiDAR Pro: la prova del robot tagliaerba con tagliabordi integrato Ecovacs Goat O1200 LiDAR Pro: la prova del robot...
Recensione Samsung Galaxy S26+: sfida l'Ultra, ma ha senso di esistere? Recensione Samsung Galaxy S26+: sfida l'Ultra, m...
Zeekr X e 7X provate: prezzi, autonomia fino a 615 km e ricarica in 13 minuti Zeekr X e 7X provate: prezzi, autonomia fino a 6...
Marathon: arriva il Fortnite hardcore Marathon: arriva il Fortnite hardcore
HP Imagine 2026: abbiamo visto HP IQ all’opera, ecco cosa può (e non può) fare HP Imagine 2026: abbiamo visto HP IQ all’opera, ...
Le 10 migliori offerte Amazon di Pasqua:...
Nuove fotografie dagli astronauti di Art...
La toilette della capsula Orion Integrit...
GeForce NOW: ecco tutte le novità in arr...
Il Realme 16 5G debutta sul mercato glob...
HONOR svela tre nuovi tablet: il più int...
Tineco Floor One S9 Master: aspira e pul...
Vivo X300 Ultra, il lancio globale è ini...
Offerte robot aspirapolvere Amazon: ECOV...
L'AI genera codice in 8 minuti e i senio...
Ring Intercom Audio a 44,99€ su Amazon: ...
Apple iPhone 16 crolla a 689€: ecco perc...
Google Pixel 9 a 449,90€ con caricatore ...
Ecco la top 7 delle offerte Amazon, aggi...
Ex ingegnere ammette il sabotaggio: migl...
Chromium
GPU-Z
OCCT
LibreOffice Portable
Opera One Portable
Opera One 106
CCleaner Portable
CCleaner Standard
Cpu-Z
Driver NVIDIA GeForce 546.65 WHQL
SmartFTP
Trillian
Google Chrome Portable
Google Chrome 120
VirtualBox
Tutti gli articoli Tutte le news Tutti i download

Strumenti

Regole
Non Puoi aprire nuove discussioni
Non Puoi rispondere ai messaggi
Non Puoi allegare file
Non Puoi modificare i tuoi messaggi

Il codice vB è On
Le Faccine sono On
Il codice [IMG] è On
Il codice HTML è Off
Vai al Forum


Tutti gli orari sono GMT +1. Ora sono le: 05:34.


Powered by vBulletin® Version 3.6.4
Copyright ©2000 - 2026, Jelsoft Enterprises Ltd.
Served by www3v