edutecnica

Streams (flussi di dati)

      

La più banale delle istruzioni Java:

System.out.println("Hallo World");

System.out è un oggetto della classe PrintStream ed appartenente al package java.io.
Si tratta di un oggetto per i trattamenti dei flussi (streams) di uscita di tipo testuale.
Un flusso o stream è un oggetto in grado di gestire una sequenza di dati ; può essere assimilato ad un canale di comunicazione che unisce una sorgente ad una destinazione.


Sia la sorgente che la destinazione possono essere entità di varia natura.

- una zona della memoria della macchina virtuale.
- un file residente su disco.
- una periferica di I/O come tastiera o video.

I tipi di flusso usati di routine sono:

System.in             flusso in ingresso associato alla tastiera
System.out           flusso in uscita associato al video
System.err            flusso di uscita per la gestione degli errori associato al video

La tecnica per creare ed elaborare dei flussi in Java è (in linea di massima) rappresentata dal seguente schema

flusso f=new flusso(parametri);
try{
operazioni di lettura/scrittura su f;
f.close();
} catch trattamenti IOException;


Nel caso specifico dei files di testo, le principali classi coinvolte sono: PrintWriter e FileWriter in output; mentre in input abbiamo le classi BufferedReader FileReader.

Per la lettura di files di testo può essere usato uno scritto come il seguente

import java.io.*;
public class leggi {
public static void main(String args[]) {
BufferedReader f=null;
String s="";
try {
   f=new BufferedReader(new FileReader("pippo.txt"));
   while(s!=null){
      System.out.println(s);
      s=f.readLine();
   }//fine while
f.close();
}catch (IOException e){
   System.err.println("errore");
   e.printStackTrace();
   System.exit(1);
}//fine try-catch
}//fine main
}//fine class

Mentre per la scrittura di un file di testo possiamo usare un programma come questo:

import java.io.*;
public class scrivi {
public static void main(String args[]) {
PrintWriter f=null;
try { //crea il file cancellando il precedente se già esiste
   f=new PrintWriter(new FileWriter("hallo.txt"));
}catch (IOException e){
   System.err.println("errore");
   e.printStackTrace();
   System.exit(1);
}//fine try-catch
//scrittura

f.println("Hallo");
f.print("World");
f.close();
}//fine main
}//fine class

L'uso di files di testo non è l'unica pratica eventuale; è noto che spesso tocca manipolare intere strutture di dati ( eterogenei fra loro ).
In altri linguaggi, come C e Pascal possono essere usati files di tipo binario e anche Java non è da meno.
Nel seguente listato ci proponiamo di scrivere su disco un file binario contenente una struttura di dati eterogenea, caratterizzata da un campo 'prd' di tipo stringa e un campo 'prz' di tipo intero.
Questa è una struttura rappresentativa degli articoli contenuti in un magazzino (con denominazione 'prd') con il loro corrispondente prezzo (con denominazione 'prz').

import java.io.*;
public class scriviobj {
public static void main(String args[]) throws IOException{
FileOutputStream f=new FileOutputStream("dati.dat");
ObjectOutputStream o=new ObjectOutputStream(f);
o.writeObject(new rec("ruota",5));
o.writeObject(new rec("biella",7));
o.close();
}//fine main
}//fine class

class rec implements Serializable {
private String prd;
private int prz;
rec (String prd,int prz){
this.prd=prd;
this.prz=prz;
}
String getPrd() {return prd;}
int getPrz() {return prz;}
}

Si nota come la classe rec implementa la classe Java.io.Serializable che impone che la struttura di dati manipolati sia 'serializzata' cioè rappresentata attraverso un sequenza di byte.

Il corrispondente programma che permette di leggere il file binario creato è questo:

import java.io.*;
public class leggiobj {
public static void main(String args[]) throws IOException, ClassNotFoundException{
FileInputStream f=new FileInputStream("dati.dat");
ObjectInputStream o=new ObjectInputStream(f);
boolean fine=false;
while(!fine){
   try{
      rec x=(rec)o.readObject();
      System.out.println(x.getPrd()+" "+x.getPrz());
   }catch (EOFException e){
      fine=true;
   }//fine try-catch
}//fine while
o.close();
}//fine main
}//fine class

class rec implements Serializable {
private String prd;
private int prz;
rec (String prd,int prz){
this.prd=prd;
this.prz=prz;
}
String getPrd() {return prd;}
int getPrz() {return prz;}
}

Come si nota, anche in questo caso è necessaria la presenza di un blocco try-catch per intercettare la fine del file (EOFException e).