Bom dia! Fiz um programa pra faculdade e estou tendo um problema com EOFException. sei que este ocorre quando o fim do arquivo é atingido inesperadamente, mas não sei como resolver neste caso! segue o código: (A exceção ocorre na linha após o while, readData = ds.readUTF()
JFileChooser jfc = new JFileChooser();
int returnval = jfc.showOpenDialog(null);
int lido = 0;
int ultimomes = -1;
if (returnval == JFileChooser.APPROVE_OPTION) {
File file = jfc.getSelectedFile();
try {
FileInputStream fs = new FileInputStream(file);
BufferedInputStream bs = new BufferedInputStream(fs);
DataInputStream ds = new DataInputStream(bs);
BufferedReader br = new BufferedReader(new InputStreamReader(fs));
while (lido != -1) {
String readData = ds.readUTF();
String saidavento = Character.toString(ds.readChar()) + Character.toString(ds.readChar());
SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy");
int velocidadevento = ds.readInt();
int pluviometro = ds.readInt();
double temperatura = ds.readDouble();
Date date = sdf.parse(readData);
Calendar cal = Calendar.getInstance();
cal.setTime(date);
ClimaDoDia clima = new ClimaDoDia(date, saidavento, velocidadevento, pluviometro, temperatura);
FileOutputStream primeiro = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
if (cal.get(Calendar.MONTH) != ultimomes) {
FileOutputStream proximo = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
ObjectOutputStream gravar = new ObjectOutputStream(proximo);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
} else {
ObjectOutputStream gravar = new ObjectOutputStream(primeiro);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
}
lido = ds.read();
}
} catch (FileNotFoundException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (IOException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (ParseException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
}
} else {
JOptionPane.showMessageDialog(null, "Usuário cancelou a operação!");
}
}
// while (lido != -1) {
while (true) { // loop infinito
try {
e
// lido = ds.read();
} catch(EOFException fim) {
ds.close(); // finaliza o stream
break; // sai do loop
}
Se ler a documentação, verá que o DataInputStream
usa a exceção para avisar que terminou de ler o arquivo e não retornará -1
no read
.
https://docs.oracle.com/javase/7/docs/api/java/io/DataInputStream.html#readUTF()
1 curtida
Sua sugestão resolveu aquele problema! mas agora estou com outro em mãos! 
Agora parece que a exceção nunca é lançada, e o loop fica infinito!
Segue o código alterado:
JFileChooser jfc = new JFileChooser();
int returnval = jfc.showOpenDialog(null);
int ultimomes = -1;
if (returnval == JFileChooser.APPROVE_OPTION) {
File file = jfc.getSelectedFile();
try {
FileInputStream fs = new FileInputStream(file);
BufferedInputStream bs = new BufferedInputStream(fs);
DataInputStream ds = new DataInputStream(bs);
BufferedReader br = new BufferedReader(new InputStreamReader(fs));
while (true) {
try {
String readData = ds.readUTF();
String saidavento = Character.toString(ds.readChar()) + Character.toString(ds.readChar());
SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy");
int velocidadevento = ds.readInt();
int pluviometro = ds.readInt();
double temperatura = ds.readDouble();
Date date = sdf.parse(readData);
Calendar cal = Calendar.getInstance();
cal.setTime(date);
ClimaDoDia clima = new ClimaDoDia(date, saidavento, velocidadevento, pluviometro, temperatura);
FileOutputStream primeiro = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
if (cal.get(Calendar.MONTH) != ultimomes) {
FileOutputStream proximo = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
ObjectOutputStream gravar = new ObjectOutputStream(proximo);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
} else {
ObjectOutputStream gravar = new ObjectOutputStream(primeiro);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
}
} catch (EOFException fim) {
ds.close();
break;
}
}
} catch (FileNotFoundException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (IOException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (ParseException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
}
} else {
JOptionPane.showMessageDialog(null, "Usuário cancelou a operação!");
}
}
Pesquisei um pouco mais, tente assim:
// while (lido != -1) {
while(ds.available()>0) {
e
// lido = ds.read();
// catch removido
https://www.tutorialspoint.com/java/java_datainputstream.htm
1 curtida
Fiz as alterações, mas o loop continua infinito! 
Não sei o que fazer!
JFileChooser jfc = new JFileChooser();
int returnval = jfc.showOpenDialog(null);
int ultimomes = -1;
int lido = 0;
if (returnval == JFileChooser.APPROVE_OPTION) {
File file = jfc.getSelectedFile();
try {
FileInputStream fs = new FileInputStream(file);
BufferedInputStream bs = new BufferedInputStream(fs);
DataInputStream ds = new DataInputStream(bs);
BufferedReader br = new BufferedReader(new InputStreamReader(fs));
while (lido != -1) {
while (ds.available() > 0) {
String readData = ds.readUTF();
String saidavento = Character.toString(ds.readChar()) + Character.toString(ds.readChar());
SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy");
int velocidadevento = ds.readInt();
int pluviometro = ds.readInt();
double temperatura = ds.readDouble();
Date date = sdf.parse(readData);
Calendar cal = Calendar.getInstance();
cal.setTime(date);
ClimaDoDia clima = new ClimaDoDia(date, saidavento, velocidadevento, pluviometro, temperatura);
FileOutputStream primeiro = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
if (cal.get(Calendar.MONTH) != ultimomes) {
FileOutputStream proximo = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
ObjectOutputStream gravar = new ObjectOutputStream(proximo);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
} else {
ObjectOutputStream gravar = new ObjectOutputStream(primeiro);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
}
}
lido = ds.read();
}
} catch (FileNotFoundException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (IOException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (ParseException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
}
} else {
JOptionPane.showMessageDialog(null, "Usuário cancelou a operação!");
}
}
private void btRelatorioActionPerformed(java.awt.event.ActionEvent evt) {
JFileChooser jfc = new JFileChooser();
int returnVal = jfc.showOpenDialog(null);
if (returnVal == JFileChooser.APPROVE_OPTION) {
FileInputStream fs = null;
try {
File file = jfc.getSelectedFile();
fs = new FileInputStream(file);
BufferedInputStream bs = new BufferedInputStream(fs);
DataInputStream ds = new DataInputStream(bs);
} catch (FileNotFoundException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (IOException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} finally {
try {
fs.close();
} catch (IOException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
}
}
} else {
JOptionPane.showMessageDialog(null, "O usuário cancelou a operação!");
}
Removi e continua infinito! poderia ser alguma particularidade do arquivo que estou tentando ler talvez?
private void btLerActionPerformed(java.awt.event.ActionEvent evt) {
JFileChooser jfc = new JFileChooser();
int returnval = jfc.showOpenDialog(null);
int ultimomes = -1;
int lido = 0;
if (returnval == JFileChooser.APPROVE_OPTION) {
File file = jfc.getSelectedFile();
try {
FileInputStream fs = new FileInputStream(file);
BufferedInputStream bs = new BufferedInputStream(fs);
DataInputStream ds = new DataInputStream(bs);
BufferedReader br = new BufferedReader(new InputStreamReader(fs));
while (ds.available() > 0) {
String readData = ds.readUTF();
String saidavento = Character.toString(ds.readChar()) + Character.toString(ds.readChar());
SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy");
int velocidadevento = ds.readInt();
int pluviometro = ds.readInt();
double temperatura = ds.readDouble();
Date date = sdf.parse(readData);
Calendar cal = Calendar.getInstance();
cal.setTime(date);
ClimaDoDia clima = new ClimaDoDia(date, saidavento, velocidadevento, pluviometro, temperatura);
FileOutputStream primeiro = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
if (cal.get(Calendar.MONTH) != ultimomes) {
FileOutputStream proximo = new FileOutputStream(cal.get(Calendar.YEAR) + "-" + cal.get(Calendar.MONTH) + ".dat");
ObjectOutputStream gravar = new ObjectOutputStream(proximo);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
} else {
ObjectOutputStream gravar = new ObjectOutputStream(primeiro);
gravar.writeObject(clima);
gravar.flush();
gravar.close();
ultimomes = cal.get(Calendar.MONTH);
}
}
} catch (FileNotFoundException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (IOException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
} catch (ParseException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
}
} else {
JOptionPane.showMessageDialog(null, "Usuário cancelou a operação!");
}
}
Poderia verificar se o ds está mudando?
while (ds.available() > 0) {
System.out.println("ds.available() : "+ds.available());
String readData = ds.readUTF();
System.out.println("readData : "+readData);
1 curtida
Esta é a saída! porém logo após ocorre uma EOFException!
ds.available() : 459
readData : 4/1/2018
ds.available() : 449
readData :
ds.available() : 369
readData : 7/1/2018
ds.available() : 359
@1ffffff8/1/2018
O arquivo que estou tentando ler tem esta ordem de tipos: String, String, Int, Int, Double e depois repete!
Provavelmente está lendo errado, para cada ds.read*
crie um System.out.println
para identificar o que está errado. Não tenho como verificar aqui.
1 curtida
Mas no código está lendo
String char char int double
1 curtida
Aparentemente está lendo tudo corretamente! São dados de diversos dias, por isso são tantos.
Saída:
ds.available() : 459
readData : 4/1/2018
Direção do vento (char + char): NE
Velocidade do vento: 20
Pluviometro: 0
Temperatura: 27.0
ds.available() : 429
readData : 5/1/2018
Direção do vento (char + char): SE
Velocidade do vento: 58
Pluviometro: 14
Temperatura: 25.2
ds.available() : 399
readData : 6/1/2018
Direção do vento (char + char): E
Velocidade do vento: 65
Pluviometro: 5
Temperatura: 18.2
ds.available() : 369
readData : 7/1/2018
Direção do vento (char + char): SW
Velocidade do vento: 50
Pluviometro: 13
Temperatura: 17.4
ds.available() : 339
readData : 8/1/2018
Direção do vento (char + char): SE
Velocidade do vento: 17
Pluviometro: 6
Temperatura: 23.0
ds.available() : 309
readData : 9/1/2018
Direção do vento (char + char): W
Velocidade do vento: 64
Pluviometro: 0
Temperatura: 21.0
ds.available() : 279
readData : 10/1/2018
Direção do vento (char + char): E
Velocidade do vento: 27
Pluviometro: 9
Temperatura: 24.6
ds.available() : 248
readData : 11/1/2018
Direção do vento (char + char): NE
Velocidade do vento: 36
Pluviometro: 2
Temperatura: 17.7
ds.available() : 217
readData : 12/1/2018
Direção do vento (char + char): SE
Velocidade do vento: 48
Pluviometro: 18
Temperatura: 22.1
ds.available() : 186
readData : 13/1/2018
Direção do vento (char + char): W
Velocidade do vento: 65
Pluviometro: 1
Temperatura: 17.4
ds.available() : 155
readData : 14/1/2018
Direção do vento (char + char): E
Velocidade do vento: 35
Pluviometro: 4
Temperatura: 22.8
ds.available() : 124
readData : 15/1/2018
Direção do vento (char + char): SW
Velocidade do vento: 12
Pluviometro: 17
Temperatura: 23.0
ds.available() : 93
readData : 16/1/2018
Direção do vento (char + char): W
Velocidade do vento: 37
Pluviometro: 0
Temperatura: 23.6
ds.available() : 62
readData : 17/1/2018
Direção do vento (char + char): NW
Velocidade do vento: 22
Pluviometro: 4
Temperatura: 23.1
ds.available() : 31
readData : 18/1/2018
Direção do vento (char + char): E
Velocidade do vento: 14
Pluviometro: 0
Temperatura: 27.3
Onde está ocorrendo a exceção?
Se for na “String readData = ds.readUTF();” seria impossível imprimir esse resultado pois antes dessa linha tem "System.out.println("ds.available() : “+ds.available());”
Então o final seria:
ds.available() : 31
readData : 18/1/2018
Direção do vento (char + char): E
Velocidade do vento: 14
Pluviometro: 0
Temperatura: 27.3
ds.available() : ?? <-- faltou essa linha
1 curtida
A exceção ocorre justamente nessa linha!
pelo que parece o programa nunca termina de ler o arquivo, porém pelo teste que fizemos antes, ele imprime todo o conteúdo do mesmo!
ds.available() : 459
readData : 4/1/2018
Direção do vento (char + char): NE
Velocidade do vento: 20
Pluviometro: 0
Temperatura: 27.0
ds.available() : 429
readData : 5/1/2018
Direção do vento (char + char): SE
Velocidade do vento: 58
Pluviometro: 14
Temperatura: 25.2
ds.available() : 399
readData : 6/1/2018
Direção do vento (char + char): E
Velocidade do vento: 65
Pluviometro: 5
Temperatura: 18.2
ds.available() : 369
readData : 7/1/2018
Direção do vento (char + char): SW
Velocidade do vento: 50
Pluviometro: 13
Temperatura: 17.4
ds.available() : 339
readData : 8/1/2018
Direção do vento (char + char): SE
Velocidade do vento: 17
Pluviometro: 6
Temperatura: 23.0
ds.available() : 309
readData : 9/1/2018
Direção do vento (char + char): W
Velocidade do vento: 64
Pluviometro: 0
Temperatura: 21.0
ds.available() : 279
readData : 10/1/2018
Direção do vento (char + char): E
Velocidade do vento: 27
Pluviometro: 9
Temperatura: 24.6
ds.available() : 248
readData : 11/1/2018
Direção do vento (char + char): NE
Velocidade do vento: 36
Pluviometro: 2
Temperatura: 17.7
ds.available() : 217
readData : 12/1/2018
Direção do vento (char + char): SE
Velocidade do vento: 48
Pluviometro: 18
Temperatura: 22.1
ds.available() : 186
readData : 13/1/2018
Direção do vento (char + char): W
Velocidade do vento: 65
Pluviometro: 1
Temperatura: 17.4
ds.available() : 155
readData : 14/1/2018
Direção do vento (char + char): E
Velocidade do vento: 35
Pluviometro: 4
Temperatura: 22.8
ds.available() : 124
readData : 15/1/2018
Direção do vento (char + char): SW
Velocidade do vento: 12
Pluviometro: 17
Temperatura: 23.0
ds.available() : 93
readData : 16/1/2018
Direção do vento (char + char): W
Velocidade do vento: 37
Pluviometro: 0
Temperatura: 23.6
ds.available() : 62
readData : 17/1/2018
Direção do vento (char + char): NW
Velocidade do vento: 22
Pluviometro: 4
Temperatura: 23.1
ds.available() : 31
readData : 18/1/2018
Direção do vento (char + char): E
Velocidade do vento: 14
Pluviometro: 0
Temperatura: 27.3
Mas não imprime o “ds.available()” ?
Então acrescente um “catch”:
} catch (EOFException ex) {
// fim
} catch (FileNotFoundException ex) {
Logger.getLogger(ClimaFrame.class.getName()).log(Level.SEVERE, null, ex);
}
Isso deve sumir com a exceção, mas acho que não resolveria o problema
A exceção só ocorria com o código para teste que você sugeriu antes!
while (ds.available() > 0) {
System.out.println("ds.available() : "+ds.available());
String readData = ds.readUTF();
System.out.println("readData : "+readData);
Porém, quando fiz o código para imprimir todos os dados, não ocorre a exceção, somente fica no loop infinito!
while (ds.available() > 0) {
try {
System.out.println("ds.available() : " + ds.available());
String readData = ds.readUTF();
System.out.println("readData : " + readData);
System.out.println("Direção do vento (char + char): " + Character.toString(ds.readChar()) + Character.toString(ds.readChar()));
System.out.println("Velocidade do vento: " + ds.readInt());
System.out.println("Pluviometro: " + ds.readInt());
System.out.println("Temperatura: " + ds.readDouble());
} catch (EOFException fim) {
ds.close();
break;
}
}
Para que complicar tanto, pode usar essa minha classe como base para seu projeto
Esse é um dos melhores jeito de se escrever um arquivo e ler
package com.gleisonmv.engine.util;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
/**
*
* @author Gleison Morgado Vasconcelos
*
*/
public class FileUtil {
/**
* Read context of file
* @param file
*
* */
public static String read(File file)
{
// Current char
int c = -1;
// Build String
StringBuilder sb = new StringBuilder();
try
{
// Read text from file
BufferedReader br = new BufferedReader(new FileReader(file));
// Read
while((c = br.read()) != -1)
{
// Append char in String
sb.append((char) c);
}
// Close the inputstream of file
br.close();
// Return the text
return sb.toString();
}
catch (Exception e)
{
// Error on read file
e.printStackTrace(System.err);
}
// File error not has content
return null;
}
public static void write(File file, String content)
{
// Create the buffered writer
try
{
// Writer of file
BufferedWriter bw = new BufferedWriter(new FileWriter(file));
// Write the content
bw.write(content);
// Flush the writer content
bw.flush();
// Close the writer
bw.close();
}
catch (IOException e)
{
// Error on write the file
e.printStackTrace(System.err);
}
}
}
1 curtida
Cara, agradeço de verdade por isso! mas como é um trabalho pra faculdade, eu provavelmente teria problemas com o professor caso usasse uma classe pra fazer essa leitura! Hahahahaha
mas obrigado de qualquer forma!
Por acaso você não teria nenhum palpite do que poderia estar ocasionando esse loop infinito? é só esse problema que me impede de terminar o trabalho! 