Pagina 1 di 7 1 2 3 ... ultimoultimo
Visualizzazione dei risultati da 1 a 10 su 61

Discussione: Gestire dati su file

  1. #1

    [PILLOLA] gestire dati su file

    Nel forum più volte vengono rivolte domande che implicano una manipolazione di dati che risiedono su file.
    Questa breve pillola non è certamente esaustiva ed omnicomprensiva ma cerca di dare un indirizzo generale a molte di queste domande.
    Da tenere presente che un db su file non sarà mai lontanamente paragonabile ad un db vero e proprio con un proprio linguaggio che lo rende maggiormente efficiente.
    In questi casi, la prima cosa da tenere presente è la struttura che daremo ai nostri dati sul file: questa deve essere standard per ogni record che inseriremo in modo da poter trattare in modo uniforme tutti i records.
    Cerchiamo di immaginare il nostro db su file strutturato in questo modo

    Ogni record su una riga

    campo1 delimitatore campo2 delimitatore campo3 caratteredifinerecord

    Come si può capire si devono tenere presenti:
    a) il delimitatore
    b) il carattere di fine record
    c) il numero di campi

    Questa struttura ricorda i files con dati in formato csv (comma separated value).
    Se apriamo un foglio di calcolo, immettiamo i dati nelle colonne A B e C in modo omogeneo (su ogni colonna c'è un tipo di dato) e salviamo questo foglio in formato csv, aprendo il file creato con un prg di lettura di file di testo (ex.Notepad) noteremo che sarà così formato:

    campo1;campo2;campo3
    dato1;dato2;dato3
    dato4;dato5;dato6

    dove il ; rappresenta il nostro delimitatore di campo e \n (che in questo caso non è visibile) il carattere di fine record.

    Vediamo, dunque, come immettere e trattare i dati in quest'ottica

    Le funzioni php che utilizzeremo sono

    file fopen fputs fclose list explode trim count time date strtoupper
    Potete vederne l'utilizzo su www.php.net immettendole come ricerca

    Supponiamo che vogliamo gestire una rubrica di indirizzi email utilizzando come separatore di campi il carattere | (naturalmente questo carattere non dovrà essere presente nei vari record ma deve essere utilizzato solo come delimitatore) e come carattere di fine record \n

    Struttura della rubrica
    data di iscrizione|nome|email\n

    Nome del file di rubrica: rubrica.txt

    SCRIVERE UN RECORD
    Per prima cosa vediamo come scrivere un record.
    Tenendo presente la struttura della rubrica, la cosa diventa molto semplice:

    codice:
     // i dati nome ed email provengono presumibilmente da un form con campi input text nome ed email
     // togliamo eventuali spazi bianchi e fine riga all'inizio ed alla fine di ogni dato
     $nome = trim($nome);
     $email = trim($email);
    
     // apriamo il file di rubrica
     $fp = fopen("rubrica.txt", "a");
    
     // scriviamo il nostro record
     fputs($fp, time()."|$nome|$email\n");
    
     // chiudiamo il file
     fclose($fp)

    VISUALIZZARE I RECORDS
    Per poter leggere i dati invece tratteremo i dati in array sfruttando la funzione file("nomefile")

    Dunque:
    codice:
     // immettiamo tutti i dati del file in un array
     $records = file("rubrica.txt");
    
     // contiamo gli elementi dell'array totale
     $numero = count($records);
     
     // scorriamo l'array
     for($x = 0; $x < $numero; ++$x)
      {
       // togliamo il carattere \n
       $records[$x] = trim($records[$x]);
    
       // immettiamo i dati del singolo record in un array
       $dati = explode("|", $records[$x]);
    
       // assegniamo a delle variabili i valori dell'array
       list($timestamp, $nome, $email) = $dati;
    
       // stampiamo i risultati a video
       echo "Data: ".date("d/m/Y", $timestamp)." Nome: $nome Email: $email
    ";
      }
    Per brevità, il codice precedente poteva essere ridotto a meno righe accorpando i vari passaggi
    codice:
     $records = file("rubrica.txt");
     for($x = 0; $x < count($records); ++$x)
      {
       list($timestamp, $nome, $email) = explode("|", trim($records[$x]));
       echo "Data: ".date("d/m/Y", $timestamp)." Nome: $nome Email: $email
    ";
      }
    Per scorrere i record dall'ultimo al primo
    codice:
      ...
     for($x=count($records); $x > 0; --$x)
      ...
    RICERCARE UN RECORD
    Bisogna innanzitutto decidere in base a quale campo effettuare la ricerca
    Quella di seguito esposta è una ricerca unsensitive (non tiene conto di maiuscole e minuscole) e con esatta corrispondenza
    Supponiamo di voler fare un ricerca in base al campo nome

    codice:
     // elaboriamo la stringa da ricercare togliendo eventuali spazi bianchi all'inizio e alla fine e convertendo tutte le lettere in maiuscolo
     $searching = trim(strtoupper("valoredaricercare"));
    
     // impostiamo una variabile di controllo
     $found = false;
    
     $records = file("rubrica.txt");
     // ciclo per scorrere i records
     for($x = 0; $x < count($records); ++$x)
      {
       list($timestamp, $nome, $email) = explode("|", trim($records[$x]));
    
       // se c'è corrispondenza, interrompe il ciclo
       if( strtoupper($nome) == $searching ) {
         $found = true;
         break;
        }
      }
    
     // stampiamo il risultato
     if($found) {
       echo "Data: ".date("d/m/Y", $timestamp)." Nome: $nome Email: $email";
      }
     else {
       echo "Non sono state trovate corrispondenze";
      }
    Naturalmente questa ricerca soffre di molte limitazioni, prima di tutte il fatto che si blocca al primo record trovato.

    MODIFICARE UN RECORD
    Data la ricerca di cui sopra potremo pensare di modificare tale record.
    Infatti basterebbe aggiungere al posto della stampa del record trovato un form
    codice:
     echo "<form name=\"modifica\" action=\"modifica.php\" method=\"post\">";
      echo "Nome : <input type=\"text\" name=\"mod_nome\" value=\"$nome\">
    ";
      echo "Email : <input type=\"text\" name=\"mod_email\" value=\"$email\">
    ";
      echo "<input type=\"hidden\" name=\"searching\" value=\"$searching\">";
      echo "<input type=\"submit\" name=\"modifica\" value=\"modifica\">";
     echo "</form>";
    e nel file modifica.php

    codice:
     $records = file("rubrica.txt");
    
     // apriamo il file rubrica.txt per rigenerarlo
     $fp = fopen("rubrica.txt", "w"); 
    
     // ciclo per scorrere i records
     for($x = 0; $x < count($records); ++$x)
      {
       list($timestamp, $nome, $email) = explode("|", trim($records[$x]));
    
       // se c'è corrispondenza stampa i nuovi valori, altrimenti stampa i vecchi
       if( strtoupper($nome) == $searching ) {
         fputs($fp, time()."|$mod_nome|$mod_email\n");
        }
       else {
         fputs($fp, $record[$x]);
        }
      }
     // chiudiamo il file
     fclose($fp);
    L'esempio citato ha il limite di modificare tutti i nomi corrispondenti alla ricerca!!!

    Faccio notare che le cose suesposte sono esemplificative, molto limitate e di concetto più che di pratica (probabilmente con più di qualche errore anche di codice).
    Per sviluppare questo tipo di codice bisogna stare molto attenti alle piccole cose.
    Gli esempi qui postati non possono essere utilizzati sic et sempliciter ma bisogna considerarli come pure esemplificazioni da poter sviluppare

    Spero che questo mio contributo possa stimolarne di nuovi in questo senso.
    E' la mia opinione ed io la condivido
    Non condivido la tua idea ma darei la vita perché tu la possa esprimere (Voltaire)
    Scrivi sul muro

  2. #2
    Dimenticavo....
    In casi del genere, è consigliabile sviluppare un sistema di assegnazione e gestione e di un campo id

    E' la mia opinione ed io la condivido
    Non condivido la tua idea ma darei la vita perché tu la possa esprimere (Voltaire)
    Scrivi sul muro

  3. #3
    Utente di HTML.it
    Registrato dal
    Sep 2000
    Messaggi
    1,175
    anche se nn uso mai i txt e preferisco (quando posso) i DB, devo ammettere che è molto interessante.
    Complimenti

    PS: Saibal a questo punto deve prendere davvero provvedimenti altrimenti il forum diventa tutto un rilievo

  4. #4
    Complimenti
    P.

  5. #5
    Complimenti boomboom.

    Non avendo mai utilizzato (con il PHP) un archiviazione su file ho un dubbio: cosa succede se due utenti richiedono l'apertura del file in scrittura nello stesso "momento" (in pratica in istanti consecutivi, ma prima che uno dei due script abbia concluso)?

  6. #6
    Si utilizza flock() per bloccare il file, in questo modo nessun altro programma o processo può accedere al file.

    http://www.php.net/manual/en/function.flock.php

    ByeZ

  7. #7
    bravo boomboom... avendo utilizzato sin dalla prima volta un database, non mi sono mai occupato di archiviare dati su file.... mi sarà molto utile quando ne avrò bisogno... alla fine è meglio usare i files quando i dati sono pochi

  8. #8
    Ciao,
    se posso aggiungo un mio contributo alle ottime spiegazioni di Boomboom:
    se ci si trova su un sistema unix/linux diventa possibile fare ricerche nei files di testo anche utilizzando le utilissime funzioni della shell come grep.
    Ad esempio per farsi restituire da un file (miofile.txt) tutte le righe che contengono la parola "ciccio" si può fare così:
    $ft= popen("grep ciccio < miofile.txt", "r");
    $result=fpassthru($ft);

    L'ho provata solo in locale (in questo periodo ho poco tempo per sperimentare) ma dovrebbe funzionare ovunque

    Domanda 1: di solito gli spazzi hosting permettono di eseguire comandi di sistema con php attraverso exec, system, o popen appunto?


    Domanda 2: la cosa si può fare anche se gli script si trovano su server Windows? Ovviamente grep non funziona ma c'è un qualche comando DOS che svolga il medesimo compito?
    per favore NIENTE PVT TECNICI da sconosciuti

  9. #9
    grazie per i suggerimenti Fabio

    La funzione DOS che cerchi dovrebbe essere FIND.EXE
    E' la mia opinione ed io la condivido
    Non condivido la tua idea ma darei la vita perché tu la possa esprimere (Voltaire)
    Scrivi sul muro

  10. #10
    Ciao Boom, che velocità!
    Sapresti farmi qualche esempio di sintassi DOS con find?
    per favore NIENTE PVT TECNICI da sconosciuti

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2024 vBulletin Solutions, Inc. All rights reserved.