I File sono archivi di dati memorizzati su memoria di massa. La creazione di un file da' la possibilita' di archiviare dati per un uso futuro, sia da parte dello stesso programma che lo ha creato sia da parte di un altro programma.
A seconda della modalita' di organizzazione dei dati su disco, ci sono diversi tipi di file:
Utilizzo dei file
I file sequenziali sono molto utili per archiviare dati di tipo testo,
sia memorizzati in forma libera (file TXT),
sia rispettando un formato (file HTML, file XML),
sia contenenti parametri di inizializzazione di un programma
(file INI), sia contenenti istruzioni di un programma sorgente (file BAS, ...).
I dati letti da un file sequenziale verranno collocati in memoria centrale, in
variabili di tipo String.
I file random sono utili per memorizzare dati strutturati sotto forma tabellare,
che sono molto usati nei problemi di natura gestionale (ad esempio l'archivio degli
studenti di una scuola e l'archivio dei voti degli studenti nelle varie materie).
Le righe di una tabella di dati si chiamano RECORD, mentre le colonne si chiamano
CAMPI.
Storicamente, la gestione dei file random e' stata via via potenziata con l'aggiunta di
meccanismi e strutture dati ausiliarie (indici) per consentire un rapido accesso ai dati
sulla base del loro contenuto (accesso con chiave)
e per garantirne la sicurezza (privatezza, tolleranza ai guasti, accesso concorrente
da parte di piu' utenti).
Questa evoluzione ha portato a complessi meccanismi di gestione dei dati in
forma tabellare, per i quali sono necessari appositi software di gestione:
si parla quindi di DATABASE (per la gestione integrata di molteplici tabelle
di dati) e di Sistemi di Gestione di Database (esempi: Access, SQL Server, Oracle,
DB2).
I dati letti da un file random verranno collocati in memoria centrale, in
variabili di tipo Tabella, ovvero Array di Record.
I file binari sono utili per memorizzare dati di qualsiasi tipo, risulta pero' tutta a carico del programma la corretta sequenza di lettura e interpretazione degli stessi: ad esempio e' possibile memorizzare in un file binario il contenuto di tutte le variabili in memoria centrale, con la necessita' di ricordare l'esatto ordine in cui sono state memorizzate, per consentirne un successivo recupero.
Operazioni di apertura e chiusura dei file
La prima operazione che si deve fare su un file e' l'Apertura (Open), che consente di associare un numero di identificazione, detto numero di Canale, ad uno specifico file memorizzato su disco.
Si parla di "numero di Canale" in quanto si interpreta un file come un "flusso di dati" che giungono dal disco fisso all'area di memoria del programma transitando lungo un "canale virtuale".
Inoltre, l'operazione di apertura associa ad un file una zona di memoria centrale, detta BUFFER, gestita dal sistema operativo per accogliere i dati letti da disco, oppure pronti per essere memorizzati su disco.
Si ricorda che l'input/output da disco, per questioni di efficienza, non avviene mai un Byte alla volta bensi' a BLOCCHI di Byte, ad esempio a blocchi di 2048 Byte; cosicche', anche se si e' interessati ad un dato lungo due Byte, si dovranno in realta' leggere dal disco 2048 Byte, dei quali solo i due che interessano verranno collocati in una qualche variabile gestita dal programma.
Se, per caso, in seguito mi interessano altri due Byte, potrei essere fortunato e trovarli gia' nel Buffer, cosicche' non occorre una effettiva lettura da disco, bensi' un semplice trasferimento di dati all'interno della memoria centrale, dal Buffer alla variabile desiderata.
Analogamente per la scrittura su disco: si accumulano nel Buffer i Byte da scrivere su disco, e solo quando il Buffer e' pieno questi dati verranno effettivamente registrati su disco.
Con l'apertura del file si associa allo stesso anche una variabile cursore che tiene traccia della posizione dove si e' arrivati a leggere, o a scrivere: si tratta di una variabile di tipo Long, gestita automaticamente da Visual Basic, che assume come valore la posizione del prossimo dato da leggere/scrivere; con "dato" si intende carattere oppure record oppure byte, rispettivamente per i file sequenziali, random e binari.
Il primo dato di un file ha convenzionalmente la posizione numero 1.
Notare che subito dopo una operazione di lettura/scrittura, il cursore non si trova posizionato sul dato appena letto/scritto, bensi' sul successivo!.
Dopo l'utilizzo del file, lo si deve Chiudere (Close), per liberare tutte le risorse di memoria impegnate dallo stesso, ed anche, per i file su cui si sta scrivendo, per comandare lo scaricamento del Buffer (operazione di Flush), ovvero scriverne il contenuto su disco.
Le altre operazioni che si possono fare su un file sono determinate dalla modalita'
di apertura dello stesso.
La sintassi dell'istruzione di apertura e' la seguente:
Open nomeFile For modalitàApertura as #numeroDiCanale [Len = lunghezzaRecord]
dove numeroDiCanale e' un numero intero da 1 a 511, e
dove Len = lunghezzaRecord
si applica soltanto ai file Random.
I file sequenziali possono essere aperti nei seguenti modi:
Input
,
Output
,
Append
.
I file random vengono aperti unicamente in modalita' Random
.
Per essi c'e' la necessita' di specificare la lunghezza del record (espressa in Byte),
ovvero la lunghezza di ciascuna riga della tabella.
I file binari vengono aperti unicamente in modalita' Binary
.
La sintassi dell'operazione di chiusura e':
Close #numeroDiCanale
Esempi:
' apro in input un file sequenziale associato al canale 1
Open "amici.txt" For Input as #1
' apro in output un file sequenziale associato al canale 2
Open "c:\documenti\nuovo.txt" For Output as #2
' apro in modalita' append un file sequenziale
nomeFile = "amici.txt"
n = FreeFile() ' funzione predefinita che restituisce il primo
' numero di canale che risulta libero
Open nomeFile For Append as #n
' apro un file random contenente un archivio di studenti
' notare che le stringhe devono essere a lunghezza fissa!
Type Studente
Nome as String*20
Classe as String*4
VotoItaliano as Integer
VotoMatematica as Integer
End Type
Dim rec as Studente
Open "studenti.dat" For Random as #1 Len = Len(rec)
' apro un file binario
n = 1
Open "foto.gif" For Binary as #n
Modalita' di accesso
La modalita' di accesso sequenziale consiste nel leggere, o scrivere, i dati uno di seguito all'altro, senza avere la possibilita' di saltare direttamente ad una determinata posizione per leggere, o scrivere, qualcosa.
Questa modalita' e' l'unica possibile quando i dati archiviati hanno lunghezza diversa.
Si pensi ad esempio ad un testo composto di righe piu' o meno lunghe: poiche' le righe
hanno un diverso numero di caratteri, l'unico modo per poter individuare la posizione
da dove inizia l'n-esima riga di testo e' leggere tutte le precedenti n-1 righe.
La modalita' di accesso diretto, invece, consiste nella possibilita'
di leggere/scrivere un dato, posizionandosi direttamente nella posizione
desiderata.
Essa presuppone che tutti i dati memorizzati
(in questo caso si parla di Record = unita' di registrazione) abbiano la stessa lunghezza
L cosicche' risulta possibile individuare immediatamente la posizione di inizio dell'n-esimo
dato:
P = (n - 1) * L + 1
Infatti, i primi n-1 record occupano complessivamente (n - 1) * L Byte, e quindi il Byte successivo e' quello da cui inizia l'n-esimo record.
Si vuole precisare che, per quanto riguarda i file binari, l'accesso diretto lo si ha a livello di Byte, ovvero si puo' saltare direttamente all'n-esimo Byte.
La modalita' di accesso con chiave , invece, consiste nella possibilita'
di leggere/scrivere un record di dati, posizionandosi direttamente su di esso
senza conoscerne la posizione bensi' conoscendone soltanto una parte del contenuto.
Tutto questo presuppone oltre che
tutti i dati memorizzati abbiano lunghezza fissa anche la presenza di
strutture dati ausiliarie per l'accesso ai dati, quali "indici" e/o strutture "hash", di cui, in questa sede, non si discutera' oltre.
Operazioni su un file sequenziale
Un file sequenziale memorizza caratteri.
Se viene aperto in Input, un file sequenziale puo' soltanto essere letto.
Di solito e' opportuno verificare che il file esista, prima di tentare di aprirlo,
con la funzione Dir$(nomeFile), la quale restituisce una stringa vuota
se nomeFile non esiste, altrimenti restituira' una stringa contenente
il nome del file medesimo. Esempio:
If Dir$("amici.txt") <>"" Then 'il file esiste
Open "amici.txt" For Input as #1
...
Close #1
Else 'il file non esiste
...
End If
Prima di qualsiasi operazione di lettura e' necessario controllare che il cursore non abbia gia' raggiunto e superato la fine del file.
Questo controllo viene fatto con la funzione booleana End Of File, EOF(numeroDiCanale).
Il programma puo' facilmente determinare se si e' o meno raggiunti la fine del file poiche' conosce la dimensione del file (essa e' fornita dal sistema operativo).
Se il cursore e' posizionato sull'ultimo carattere del file allora la condizione EOF risulta Falsa, se invece esso e' posizionato oltre l'ultimo carattere, allora essa risulta Vera.
Subito dopo l'apertura, il cursore si trova posizionato sul primo Byte; qualora il file aperto sia vuoto, la condizione EOF risulta immediatamente Vera.
Mano a mano che si leggono i caratteri memorizzati nel file, il cursore viene automaticamente fatto avanzare, in modo da puntare sempre al carattere successivo all'ultimo che e' stato letto.
Le istruzioni di lettura sono Input e Line Input e c'e' anche la funzione Input().
Se i dati memorizzati nel file sono separati da virgola, come ad esempio le seguenti due righe di dati:
"Salve", 234
"Ciao", 24
allora conviene leggerli con l'istruzione Input.
In effetti la memorizzazione avviene interponendo la coppia di caratteri CR e LF tra i dati di una riga e quelli della successiva:
"Salve", 234CRLF"Ciao", 24
Il "formato CSV" (Comma Separated Values = Valori Separati da Virgola) rappresenta un utilissimo modo per scambiare valori di forma tabellare tra programmi diversi: ad esempio da Excel ad un programma scritto in Visual Basic.
Una porzione di codice per la lettura del file puo' essere il seguente:
Dim a as String
Dim n as Integer
Open "prova.csv" For Input As #1 ' Apre il file e pone il cursore sul primo car.
Do While Not EOF(1) ' Ripete fino alla fine del file
Input #1, s, n ' Legge i dati nelle variabili e fa avanzare il cursore
MsgBox "Ho letto" & s & " e " & CStr(n) ' Messaggio di verifica
Loop
Close #1 ' Chiude il file
Notare che, per una corretta lettura, e' necessario conoscere la "struttura" di ciascuna riga di dati del file.
Se i dati sono memorizzati nel file come testo libero come ad esempio (le righe sono sempre separate dalla coppia di caratteri CR e LF):
Questa e' una lettera
da leggere
con molta
attenzione perche' e' molto interessante.
Conviene leggere il file una riga alla volta, con l'istruzione Line Input,
come illustrato dal seguente esempio:
Dim riga as String
Open "lettera.txt" For Input As #1 ' Apre il file
Do While Not EOF(1) ' Ripete fino alla fine del file
Line Input #1, riga ' Assegna la riga a una variabile
MsgBox riga ' Messaggio di verifica
Loop
Close #1 ' Chiude il file
E' anche possibile leggere tutto il file con un'unica istruzione, facendo
uso della funzione Input(numeroDiByte, numeroDiCanale) e della funzione LOF(numeroDiCanale) la quale restituisce la lunghezza del
file (Length Of File) espressa in Byte, ovvero
il numero di caratteri che costituiscono il file. Esempio:
Dim s as String
Open "pagina.htm" For Input As #1
s = Input (LOF(1), 1) ' leggo interamente il file HTML
Close #1
Se un file sequenziale viene aperto in modalita' Output, oppure Append, e' possibile soltanto effettuare l'operazione di scrittura.
Nel primo caso si crea il file, mentre nel secondo si utilizza un file preesistente.
Di solito e' opportuno verificare che il file non esista, prima di tentare di aprirlo
in modalita' Output, per evitare di sovrascrivere il contenuto di un file gia' esistente:
Viceversa per l'apertura in modalita' Append.
If Dir$("amici.txt") = "" Then 'il file non esiste
Open "amici.txt" For Output as #1
...
Close #1
Else 'il file esiste
...
End If
Per scrivere in un file sequenziale si possono usare le istruzioni Print e Write, la prima consente di scrivere un testo libero costituito da piu' righe separate dalla coppia di caratteri CR e LF, mentre la seconda consente di scrivere i dati contenuti in piu' variabili separandoli da virgola.
Entrambe aggiungono automaticamente ai dati da scrivere la coppia di caratteri CR e LF per ottenere il "ritorno a capo".
Esempio con Print:
Si ottiene:
Open "lettera.txt" For Output As #1 ' Apre il file per l'output
Print #1, "Questa � una prova" ' Scrive il testo nel file
Print #1, ' Scrive una riga vuota nel file
Print #1, "Salve gente"
Print #1, "il valore e' " & CStr(500)
Close #1
Questa � una prova
Salve gente
il valore e' 500
Anzi, piu' precisamente:
Questa � una provaCRLFCRLFSalve gente
CRLFil valore e' 500CRLF
Esempio con Write:
Si ottiene
Dim s as String
Dim n as Integer
' CSV sta per Comma Separated Values (valori separati da virgola)
Open "prova.csv" For Output as #1
s = "Salve"
n = 234
Write #1, s, n
Write #1, "Ciao", 24
Close #1 ' Chiude il file.
"Salve", 234
"Ciao", 24
Anzi, piu' precisamente:
"Salve", 234CRLF"Ciao", 24CRLF
Non e' possibile modificare direttamente un file sequenziale, e' necessario aprirlo in Input, leggerne il contenuto e trascriverlo, con le modifiche desiderate, in un altro file aperto in Output.
Operazioni su un file random
Nei file random si memorizzano tipicamente dei Record, di cui si deve dichiarare la struttura con l'istruzione Type.
Ad esempio per dichiarare il tipo Articolo, che descrive ciascun articolo presente in un magazzino di merci:
Private Type Articolo
Codice as String*4
Descrizione as String*20
PrezzoUnitario as Currency
Quantit�InGiacenza as Double
End Type
I record devono essere a lunghezza fissa, per consentire
l'accesso diretto agli stessi.
La dimensione del record deve
essere specificata nell'istruzione Open
.
L'istruzione Open apre un file random esistente oppure crea un nuovo file random.
Per scrivere si usa l'istruzione Put
e per leggere l'istruzione
Get
.
La sintassi e' rispettivamente:
Put #numeroDiCanale, posizione, variabileDaScrivere
Get #numeroDiCanale, posizione, variabileDaLeggere
dove il parametro posizione e' un numero di tipo Long che specifica la posizione a partire dalla quale leggere/scrivere la variabile indicata. Se omesso si intende la posizione corrente del cursore, che subito dopo l'apertura del file si trova sul primo record, ovvero alla posizione numero 1.
Per conoscere la posizione corrente del cursore si usa la funzione Seek(numeroDiCanale)
, la quale restituisce un numero Long
che rappresenta la posizione del record corrente, ovvero il prossimo che
sara' letto/scritto.
Il cursore avanza automaticamente a seguito delle operazioni di lettura/scrittura
Il cursore puo' essere posizionato direttamente
su qualsiasi record del file, oppure subito dopo l'ultimo record presente
in modo da consentire l'aggiunta di nuovi record allo stesso.
Per scorrere in modo sequenziale un file random, si puo' usare la condizione
EOF, vista per i file sequenziali.
Per poter aggiungere un nuovo record si deve innanzitutto determinare il numero di record
presenti con l'espressione:
dove LOF(numeroDiCanale) fornisce la lunghezza in Byte del file;
e poi posizionare il cursore alla posizione successiva con l'istruzione:
Esempio: caricamento in un file random dei dati di una tabella memorizzata
in un array.
Esempio: aumento del 10% dei prezzi di tutti gli articoli.
Un file binario memorizza byte.
L'istruzione di apertura di un file binario lo crea se esso non esiste!
Si scrive con l'istruzione
Esempio: la memorizzazione di un array di Integer:
Esempio:
oppure, lo stesso risultato puo' essere ottenuto nel seguente modo:
Quando si lavora con i file ci sono molte situazioni che possono causare
un errore run-time che interrompe l'esecuzione del programma,
quali ad esempio il tentativo di aprire in input un file non esistente,
il tentativo di leggere dati oltre la fine del file, il tentativo di
usare un numero di canale gia' in uso da parte di un altro file, ecc...
Per evitare la brusca interruzione del programma e dare
eventualmente all'utente la
possibilita' di ritentare l'operazione, ad esempio correggendo il nome
del file da aprire in input, e' opportuno introdurre un meccanismo
di intercettazione degli errori run-time.
Si utilizza l'istruzione
per saltare all'etichetta indicata ed eseguire le istruzioni
che la seguono.
L'oggetto predefinito
Il seguente esempio illustra un possibile modo di gestire l'apertura
di un file da floppy disk:
Il seguente esempio arricchisce il precedente, fornendo anche la possibilita'
di ritentare qualora il file da aprire non esista:
La seguente tabellina elenca i principali errori run-time che
riguardano l'accesso a file su disco.
Ci si rende subito conto che una gestione, seppur minimale, degli errori
complica alquanto la scrittura dei programmi.
Operazioni di servizio sui file
Visual Basic fornisce alcune istruzioni utili per la manutenzione dei file.
Ad esempio e' possibile cancellare un file con l'istruzione:
che accetta anche i caratteri jolly:
E' possibile copiare un file con l'istruzione:
E' possibile rinominare un file con l'istruzione:
Affiche' le suddette istruzioni possano funzionare, i file su cui agiscono
non devono essere aperti.
Get
e Put
; tuttavia per
sfruttare la possibilita' di accesso diretto
si deve impostare la posizione del cursore
sul record desiderato con l'istruzione Seek
: Seek #numeroDiCanale, posizione
n = LOF(numeroDiCanale) / Len(record)
Seek #numeroDiCanale, n + 1
Private Type Articolo
Codice as String*4
Descrizione as String*20
PrezzoUnitario as Currency
Quantit�InGiacenza as Double
End Type
Private Sub CaricaFile(ByRef arr() as Articolo)
Dim rec as Articolo
Dim i as Long
Open "articoli.dat" For Random as #1 Len = Len(rec)
For i = 0 To UBound(arr)
Put #1,,arr(i)
Next i
Close #1
End Sub
Operazioni su un file binario
Private Sub AumentaPrezzi()
Dim rec as Articolo
Dim posizione as Long
Open "articoli.dat" For Random as #1 Len = Len(rec)
Do While Not EOF(1)
Get #1,,rec ' legge un record
rec.PrezzoUnitario = rec.PrezzoUnitario * 1.10
posizione = Seek(1) - 1 ' determina la posizione del record appena letto
Seek #1, posizione ' posiziona il cursore sul record appena letto
Put #1,,rec ' riscrive il record con i dati modificati
Loop
Close #1
End Sub
Put
e si legge con l'istruzione
Get
.
Esempio di scrittura:
Esempio di lettura, il numero di Byte che vengono letti dipende dalla variabile usata nell'istruzione Get:
Dim n as Integer
Dim b as Byte
Dim f as String*10
Dim s as String
n = 5800
b = 1
f = "1234" ' si ottiene la stringa "1234 "
s = "abcdefghijklmnopqrst" ' stringa di 20 caratteri
' (corrisponde a 20 Byte su disco)
Put #1,,n ' scrive 2 Byte
Put #1,,b ' scrive 1 Byte
Put #1,,f ' scrive 10 Byte
Put #1,,s ' scrive 20 Byte
Si nota che per leggere correttamente si deve ricordare l'esatta sequenza delle variabili che sono state scritte.
Dim n as Integer
Dim b as Byte
Dim f as String*10
Dim s as String
s = Space$(20) 'si prepara ad accogliere 20 byte
Get #1,,n ' legge 2 Byte
Get #1,,b ' legge 1 Byte
Get #1,,f ' legge 10 Byte
Get #1,,s ' legge 20 Byte
Esempio: la lettura di un array di Integer:
Private Sub MemorizzaArray(ByRef arr() as Integer)
Dim n as Long
n = UBound(arr)
Open "array.bin" For Binary as #1
Put #1,,n ' memorizzo la dimensione dell'array
Put #1,,arr() 'memorizzo il contenuto dell'array
Close #1
End Sub
Per leggere un file binario un Byte alla volta, si deve controllare
di andare oltre la lunghezza del file con le funzioni:
Private Function CaricaArray() as Integer()
Dim n as Long
n = UBound(arr)
Open "array.bin" For Binary as #1
Get #1,,n ' legge la dimensione dell'array
ReDim CaricaArray(n) as Integer ' dimensiona l'array
Get #1,,arr() 'memorizzo il contenuto dell'array
Close #1
End Sub
Seek(numeroDiCanale)
che restituisce un valore Long che
specifica la posizione del Byte corrente del cursore di lettura/scrittura, e
LOF(numeroDiCanale)
che restituisce un valore Long che
specifica la lunghezza del file espressa in Byte.
Dim b as Byte
Open "prova.bin" For Binary as #1
Do While Seek(1) <= LOF(1)
Get #1,,b ' legge il byte corrente
...
Loop
Close #1
Dim b as Byte
Dim i as Long
Open "prova.bin" For Binary as #1
For i = 1 to LOF(1)
Get #1,,b ' legge il byte corrente
...
Next i
Close #1
Private Sub FileSplitter()
Dim maxSize as Long
Dim j as Long
Dim n as Long
Dim nomeFileInput as String
Dim nomeFileOutput as String
Dim nomeFile as String
Dim estensioneFile as String
Dim b() as Byte
nomeFileInput = InputBox("Nome del file da suddividere:") ' es.: ALFA.DOC
nomeFile = Left$(nomeFileInput, Len(nomeFileInput)-4)
estensioneFile = Right$(nomeFileInput, 3)
maxSize = InputBox("Dimensione massima da ottenere (in KByte):")
j = 0 ' contatore
Open nomeFileInput For Binary as #1
Do While Seek(1) <= LOF(1)
j = j + 1
' creo il nome del j-esimo file di output - esempio ALFA001.DOC
nomeFileOutput = nomeFile & Format(j, "000") & "." & estensioneFile
Open nomeFileOutput For Binary as #2
' supp. di avere la funzione Min(x,y) che da' il minimo di due valori
' n sara' il numero di Byte da leggere
n = Min(1024*maxSize, LOF(1) - Seek(1) + 1)
ReDim b(1 to n)
Get #1,,b
Put #2,,b
Close #2
Loop
Close #1
MsgBox "Lavoro finito!"
End Sub
Intercettazione degli errori
Private Sub FileJoiner()
Dim maxSize as Long
Dim j as Long
Dim n as Long
Dim nomeFileInput as String
Dim nomeFileOutput as String
Dim nomeFile as String
Dim estensioneFile as String
Dim b() as Byte
Dim finito as Boolean
finito = False
nomeFileInput = InputBox("Nome dei file da riassemblare:") ' es.: ALFA*.DOC
nomeFile = Left$(nomeFileInput, Len(nomeFileInput)-5)
estensioneFile = Right$(nomeFileInput, 3)
nomeFileOutput = nomeFile & "." & estensioneFile
Open nomeFileOutput For Binary as #1
j = 0 ' contatore
Do While not finito
j = j + 1
' creo il nome del j-esimo file di input - esempio ALFA001.DOC
nomeFileInput = nomeFile & Format(j, "000") & "." & estensioneFile
If Dir$(nomeFileInput)="" Then ' il file non c'e'
finito = True
Else
Open nomeFileInput For Binary as #2
n = LOF(1)
ReDim b(1 to n)
Get #2,,b
Put #1,,b
Close #2
End If
Loop
Close #1
MsgBox "Lavoro finito!"
End Sub
On Error GoTo etichetta
Err
fornisce le utili proprieta'
Err.Number
e Err.Description
che consentono di risalire, rispettivamente, al codice numerico e alla descrizione dell'errore generato.
Private Sub cmdOK_Click()
Dim isOpen As Boolean
Dim s As String
On Error GoTo Gestione_Errore 'in caso di errore lo rimanda al gestore
isOpen = False ' ora il file non e' aperto
Open "a:\pippo.txt" For Input As #1
isOpen = True ' se arrivo qui allora il file e' aperto
Do While Not EOF(1)
Input #1, s
MsgBox s
Loop
Close #1
Exit Sub ' Esco dalla Sub saltando le istruzioni che seguono!
Gestione_Errore:
' si puo' fornire il messaggio di errore:
MsgBox CStr(Err.Number) & " - " & Err.Description
' si puo' eventualmente chiedere se si vuole ritentare:
If Err.Number = 71 ' errore "disco non pronto"
Risposta = MsgBox("vuoi riprovare?", vbYesNo)
If Risposta = vbYes Then Resume ' ritorna ad eseguire l'istruzione
' che ha causato l'errore
End If
If isOpen Then Close #1 ' chiudo il file se e' rimasto aperto
End Sub
Private Sub cmdOK_Click()
Dim isOpen As Boolean
Dim s As String
Dim nomeFile as String
On Error GoTo Gestione_Errore 'in caso di errore lo rimanda al gestore
isOpen = False ' ora il file non e' aperto
nomeFile = InputBox ("Nome del file da aprire:")
Open nomeFile For Input As #1
isOpen = True ' se arrivo qui allora il file e' aperto
Do While Not EOF(1)
Input #1, s
MsgBox s
Loop
Close #1
Exit Sub ' Esco dalla Sub saltando le istruzioni che seguono!
Gestione_Errore:
' si puo' fornire il messaggio di errore:
MsgBox CStr(Err.Number) & " - " & Err.Description
' si puo' eventualmente chiedere se si vuole ritentare:
If Err.Number = 53 Then ' errore "impossibile trovare il file"
nomeFile = InputBox("Nome del file da aprire")
If nomeFile <> "" Then
Resume ' ritenta
Else
MsgBox "... allora sara' per un'altra volta"
End If
End If
If Err.Number = 71 Then ' errore "disco non pronto"
Risposta = MsgBox("Vuoi riprovare?", vbYesNo)
If Risposta = vbYes Then
Resume ' ritenta
Else
MsgBox "... allora sara' per un'altra volta"
End If
End If
If isOpen Then Close #1 ' chiudo il file se e' rimasto aperto
End Sub
CODICE ERRORE DESCRIZIONE 52 "Nome o Numero di file non valido"
oppure cerco di leggere da un file
che non e' stato aperto53 "Impossibile trovare il file"
riguarda ad es. le istruzioni Open, Kill, Name54 "Modalit� file non valida"
ad es.: Put o Get usati per file che non sono Random ne' Binary
Print# usato per file aperti in Input
Input# usato per file aperti in Output o Append 55 "File gia' aperto"
si verifica quando tento di aprire un file che risulta gia' aperto57 "Errore di I/O sulla periferica"
errore di I/O da disco o su stampante58 "File gia' esistente" 59 "Lunghezza del record non valida" 61 "Disco pieno" 62 "Input oltre la fine del file" 63 "Numero di record non valido" 67 "Troppi file aperti" 67 "Periferica non disponibile"
causato ad es. da una connessione di rete interrotta70 "Autorizzazione negata" 71 "Disco non pronto" 75 "Errore di accesso al percorso/file" 76 "Impossibile trovare il percorso"
Kill "amici.txt"
Kill "*.txt"
FileCopy "c:\documenti\sorgente.txt", "c:\temp\destinazione.txt"
FileCopy "lavoro.dat", "lavoro.bak"
Name "vecchio.txt" as "nuovo.txt"