[RESOLVIDO] OutOfMemoryError quando tento abrir arquivos

Olá, pessoal!

Estou desenvolvendo um sistema para pocket que deverá abrir arquivos texto.
No começo eu tive problemas para percorrer o arquivo, pois eu demorava 10 minutos para percorrer todo o arquivo.
Agora eu consegui resolver isso: Como o J2ME não tem suporte à classe BufferedReader, eu peguei o código da classe BufferedReader J2SE e o adaptei para J2ME, podendo assim usar o método readLine(). Assim, eu acabei baixando esse tempo para 3 segundos!!

Bom gente, agora estou com outro problema!
Preciso abrir arquivos de 2 megas mas dá OutOfMemoryError só de abrir o arquivo.

Dá erro neste método:

public BufferedReader(String nomeArquivo, int size) { in = new InputStreamReader(getClass().getResourceAsStream(nomeArquivo)); if (size <= 0) { throw new IllegalArgumentException("Illegal buffer size: " + size); } buffer = new char[size]; }

quando o java vai executar o in = new InputStreamReader(getClass().getResourceAsStream(nomeArquivo)); dá o erro.

Não sei qual é o problema, se eu só referenciando o arquivo.
Existe outra maneira de abrir arquivo em J2ME?

Grata a todos!

Vc adaptou BufferedReader de J2SE para J2ME?
Hehehe…
Tem motivo para certas classes nao estarem disponiveis nos profiles de J2ME, isso por questao de performance ou pela falta de certos recursos para se utilizar no celular.
Leitura de arquivo como te disse em outro post, eh complicado.
Vc tem qi ter um controle do seu heap size para nao dar OutOfMemoryException.

Seu size qi vc passou eh de quanto?
Ali seu provavel erro eh qi vc tentou ja instanciar 2MB na Heap do seu PDA e com certeza vc nao tem esses 2MBs, logo vc tem qi ir lendo caractere a caractere do arquivo.

Bom…

O problema do erro não é com a classe BufferedReader. Dá esse erro quando eu tento usar a InputSteamReader ou qualquer outra classe de manipulação de arquivos.
Eu tive que adaptar a classe BufferedReader pra aumentar a velocidade de leitura de arquivos textos, e consegui.

Mas eu estou com esse problema agora e mesmo quando eu tento ler caractere a caractere dá esse erro na hora de abrir o arquivo.
Como eu faço pra controlar o heap size via código de programação??

Vc nao “controla” o heap size.
Heap size eh uma area de alocamento de memoria. Em Java tem Stack e Heap size, qi eh aonde seu objetos estao alocados.

Vc pode ter ganhado performance ao custo de ter aumentado o consumo de memoria com bufferedreader.

E o qi acontece ai qi da OutMemoryEx eh qi vc esta alocando mtos objetos na memoria.

O qi vc faz ate chegar ai?

[quote=Sagatiba]Vc pode ter ganhado performance ao custo de ter aumentado o consumo de memoria com bufferedreader.

E o qi acontece ai qi da OutMemoryEx eh qi vc esta alocando mtos objetos na memoria.

O qi vc faz ate chegar ai?
[/quote]

Como eu disse: tenho certeza que não é a BufferedReader que está causando o erro. Este erro está dando faz tempo… eu só quero saber se tem como abrir esse arquivo de 2Mb sem dar erro. Tem outra forma de abrir sem ser usar essa rotina: b[/b]???

Mas, respondendo a sua pergunta: essa rotina em negrito é a primeira coisa que eu executo para abrir o arquivo. Não tem nada antes disso. Eu só passo o caminho do arquivo, e essa rotina teria que retornar um InputStream, mas em arquivos maiores que 1,8 ou 1,9 Mb dá erro.
Por isso que eu acho que é alguma coisas nesse código aí

Obrigada

Poize, mas estou tentando te explicar como funciona a questao de memoria em uma KVM para qi vc entenda o qi esta dando de erro e nao fique + no xutar e acertar.
Vamos la.
Vc tem duas areas de memoria Stack e Heap
-Variaveis de Instancia e Objetos ficam na heap.
-Variaveis locais e metodos ficam na Stack (ou pilha)

Qndo vc faz um metodo recursivo que da loop vc estoura a pilha. Qndo vc aloca mtos objetos vc estoura a heap.
Alem disso, vc deve ter um projeto em um jar size gigantesco, e um numero gigantesco de classes, alem de string e outros objetos estaticos.

Toda KVM roda em cima de uma area de memoria no aparelho, esse PDA deve ter um limite de area de memoria, ai se for uma J9 que me lembro o maximo era 4MB de heaps e o default (padrao) era 2MBs configurados.

Um dos erros qi vc deve ter feito ai, qndo vc “adaptou” bufferedreader vc trouxe umas 10 classes juntos correto?
Outra coisa eh, qndo vc esta fazendo seus metodos de leitura de caracteres, vc limpa os objetos que vc alocou antigamente e chamou explicitamente o garbage collector? System.gc()?

Essas sao as causas de se estourar memoria.

Ah, esse topico tb tinha qi ser em JavaME e nao aki.

[quote=eliangela][quote=Sagatiba]Vc pode ter ganhado performance ao custo de ter aumentado o consumo de memoria com bufferedreader.

E o qi acontece ai qi da OutMemoryEx eh qi vc esta alocando mtos objetos na memoria.

O qi vc faz ate chegar ai?
[/quote]

Como eu disse: tenho certeza que não é a BufferedReader que está causando o erro. Este erro está dando faz tempo… eu só quero saber se tem como abrir esse arquivo de 2Mb sem dar erro. Tem outra forma de abrir sem ser usar essa rotina: b[/b]???

Mas, respondendo a sua pergunta: essa rotina em negrito é a primeira coisa que eu executo para abrir o arquivo. Não tem nada antes disso. Eu só passo o caminho do arquivo, e essa rotina teria que retornar um InputStream, mas em arquivos maiores que 1,8 ou 1,9 Mb dá erro.
Por isso que eu acho que é alguma coisas nesse código aí

Obrigada[/quote]

Dei uma olhada na especificação MIDP 2.0, e não achei FileInputStream por lá, achei apenas nas especificações do CDC (para dispositivos com um tantinho a mais de recursos). Se diversos dispositivos não conseguem usar o “(getClass().getResourceAsStream(nomeArquivo))” com esses arquivos de 2 Mb, acho que uma boa solução poderia ser quebrar esse arquivo de 2 Mb em arquivos menores e ir lendo os diversos arquivos menores conforme seja necessário.

Inté.

Desculpa por colocar este tópico aqui, mas eu tinha colocado no J2ME e não tive muitas respostas. Aqui estou tendo mais respostas.
Bom… mas eu vou seguir esses passos que vc me passou e qualquer coisa posto a solução ou outra pergunta.

Muito obrigada!

[quote=KWill]
Dei uma olhada na especificação MIDP 2.0, e não achei FileInputStream por lá, achei apenas nas especificações do CDC (para dispositivos com um tantinho a mais de recursos). Se diversos dispositivos não conseguem usar o “(getClass().getResourceAsStream(nomeArquivo))” com esses arquivos de 2 Mb, acho que uma boa solução poderia ser quebrar esse arquivo de 2 Mb em arquivos menores e ir lendo os diversos arquivos menores conforme seja necessário.

Inté.[/quote]

Muito obrigada pessoal… eu realmente não sabia que existia uma diferença tão grande entre CDC e CLDC, heheh
Agora estou usando CDC e meus problemas acabaram!

Valeu!