abaixo estou colocaando meu codigo que tem com o objetivo criar um arquivo com um tamanho definido(atributo tamanho) no entanto ,verifiquei os seguintes erros:
1- O arquivo criado ,tem caracteres bem malucos ,eu coloquei abaixo uma rotina pra gerar um byte (entre 65 e 90) ou seja,quando passaria pra tipo char deveria ser “A”-“Z”.
2-O arquivo não esta tendo o tamanho exato que o atributo indica não,parece que enquanto esta sendo checado o tamanho do arquivo ,o laço while continua…e continua bombardeando o arquivo com mais carateres…ou seja ,não ha consistencia no tamanho do arquivo.Eu queria fazer uma rotina pra CRIAR um arquivo com tamanho EXATO de bytes ,e seu conteudo seja caracteres de “A” a “Z” randomicamente.
O probblema é que é uma arquivo texto de tamanho de 500mega que estou precisando gerar,abaixo tem um codigo bem simples de teste de como posso fazer isso ,no entanto quando quis fazer um arquivo de tal tamanho ,demorou quase 4 hs e só gerou em torno de 128 mega,será que alguem poderia me dar sugestões ou melhoramentos que eu poderia fazer pra gerar tal extenso arquivo?
Codigo:
importjava.io.*;importjava.lang.*;importjavax.swing.*;publicclassArquivo{inttamanho;publicArquivo(inttam){tamanho=tam;}publicvoidinicializa(){try{Filefile=newFile("data.txt");FileWriterarquivo=newFileWriter(file);BufferedWriterbuffer=newBufferedWriter(arquivo);intbyteGerado=0;charcharGerado;intcount=0;for(;;){byteGerado=65+(int)(Math.random()*26);count++;arquivo.write((char)byteGerado);count++;if(count>=tamanho)break;}buffer.close();arquivo.close();System.out.println("Foi gerado "+count+" Bytes e tamanho eh"+file.length());}catch(IOExceptionie){System.out.println("ERROR-"+ie.toString());}catch(SecurityExceptionse){System.out.println("ERROR-"+se.toString());}}publicstaticvoidmain(Stringargs[]){//tamanho do arquivointt=30000;Arquivoa=newArquivo(t);System.out.println("SISTEMA INICIADO");a.inicializa();}}
importjava.io.BufferedWriter;importjava.io.File;importjava.io.FileWriter;importjava.io.IOException;publicclassArquivo{inttamanho;publicArquivo(inttam){tamanho=tam;}publicvoidinicializa(){try{Filefile=newFile("data.txt");FileWriterarquivo=newFileWriter(file);BufferedWriterbuffer=newBufferedWriter(arquivo);intbyteGerado=0;charcharGerado;intcount=0;for(count=0;count<tamanho;count++){byteGerado=65+(int)(Math.random()*26);buffer.write((char)byteGerado);}buffer.flush();buffer.close();System.out.println("Foi gerado "+count+" Bytes e tamanho eh "+file.length());}catch(IOExceptionie){ie.printStackTrace();}}publicstaticvoidmain(Stringargs[]){// tamanho do arquivointt=30000;Arquivoa=newArquivo(t);System.out.println("SISTEMA INICIADO");a.inicializa();
Modificações:
:arrow: corrigi os imports
:arrow: retirei a declaração da variável charGerado (não está sendo usada)
:arrow: você estava escrevendo em arquivo ao invés de escrever no buffer (foi isso que ocasionou a lentidão)
:arrow: você estava usando count++ duas vezes (o uso padrão do for evita esse tipo comum de erro)
:arrow: é bom executar um flush antes de fechar o buffer (para ter certeza que o buffer foi descarregado completamente)
:arrow: basta fechar o buffer (não precisa fechar o arquivo)
:arrow: Para as exeções, printStackTrace gera informações mais detalhadas que usar toString
A execução desse código em minha máquina foi instantânea.
H
HumbertoJrPJ
"vinci":
Olá,
Olhe seu código refatorado:
importjava.io.BufferedWriter;importjava.io.File;importjava.io.FileWriter;importjava.io.IOException;publicclassArquivo{inttamanho;publicArquivo(inttam){tamanho=tam;}publicvoidinicializa(){try{Filefile=newFile("data.txt");FileWriterarquivo=newFileWriter(file);BufferedWriterbuffer=newBufferedWriter(arquivo);intbyteGerado=0;charcharGerado;intcount=0;for(count=0;count<tamanho;count++){byteGerado=65+(int)(Math.random()*26);buffer.write((char)byteGerado);}buffer.flush();buffer.close();System.out.println("Foi gerado "+count+" Bytes e tamanho eh "+file.length());}catch(IOExceptionie){ie.printStackTrace();}}publicstaticvoidmain(Stringargs[]){// tamanho do arquivointt=30000;Arquivoa=newArquivo(t);System.out.println("SISTEMA INICIADO");a.inicializa();
Modificações:
:arrow: corrigi os imports
:arrow: retirei a declaração da variável charGerado (não está sendo usada)
:arrow: você estava escrevendo em arquivo ao invés de escrever no buffer (foi isso que ocasionou a lentidão)
:arrow: você estava usando count++ duas vezes (o uso padrão do for evita esse tipo comum de erro)
:arrow: é bom executar um flush antes de fechar o buffer (para ter certeza que o buffer foi descarregado completamente)
:arrow: basta fechar o buffer (não precisa fechar o arquivo)
:arrow: Para as exeções, printStackTrace gera informações mais detalhadas que usar toString
A execução desse código em minha máquina foi instantânea.
Cara obrigado pela ajuda mas essa versão que eu postei aqui era uma que eu tinha no e-mail ,diferente da correta que eu tinha em casa.....e que não tem os erros tão primarios quanto os que vc me chamou a atenção....
Mas o detalhe é que preciso gerar um arquivo de 500 MEGA! Isso não é nada instantaneo nem na sua versão(que está com a variavel "tam" gerando apenas 30000 bytes)
tem como eu gerar esse arquivo de 500 MEGA BYTES de forma eficiente?
Cara ,por favor,eu não entendi esse 1024! O que ele favorece pra criar um arquivo de 500MEGAs?
V
vinciPJ
Ele especifica o tamanho do buffer. Com esse valor, o arquivo de 500 megas foi gerado em cerca de 2 minutos. Esse já é um tempo razoável para você?
H
HumbertoJrPJ
Uaaaaaaaaaaaaaaaauuuuuu 2 minutos?
Caramba isso que é otimização! Os colegas que fizeram em VB tavam levando horas( e eu tb) ,tem certeza mesmo que gerou 500 MegaBytes(metade de 1 Giga) em 2 minutos apenas?
:lol: :lol: :lol: :lol: Se for mesmo …vc é o cara mesmo!
Mas me explica só uma coisa ,o buffer que esta sendo usado então tem 1024 bytes,é isso mesmo que entendi?
V
vinciPJ
Olha, eu gastei um pouco menos de 2 minutos aqui na minha máquina sim. É claro que isso pode variar de acordo com a configuração. Teste e diga qual foi o seu resultado.
É isso mesmo, 1024 bytes é o tamanho do buffer.
H
HumbertoJrPJ
“vinci”:
Olha, eu gastei um pouco menos de 2 minutos aqui na minha máquina sim. É claro que isso pode variar de acordo com a configuração. Teste e diga qual foi o seu resultado.
É isso mesmo, 1024 bytes é o tamanho do buffer.
ei cara só mais um aduvioda ja que vc entende tudo de arquivo,como estou gerando 1 arquivo de caracteres sem nenhuma ordenação ,ele vai querer ordenar isso mas pelo tamanho dele ,não dará pra ordenar tudo de uma vez e pergunto se a estrutura Buffer é o mais recomendado mesmo pra ordenação de blocos do arquivo? é a famosa ordenção externa mesmo usando alguns metodos…
H
HumbertoJrPJ
“vinci”:
Olha, eu gastei um pouco menos de 2 minutos aqui na minha máquina sim. É claro que isso pode variar de acordo com a configuração. Teste e diga qual foi o seu resultado.
É isso mesmo, 1024 bytes é o tamanho do buffer.
Acho que até 5 min meu prof não deve me trucidar… 8O
Valeu mesmo!ei cara só mais uma duvida ja que vc entende tudo de arquivo,como estou gerando 1 arquivo de caracteres sem nenhuma ordenação ,ele vai querer ordenar isso a posteriori ,mas pelo tamanho dele ,não dará pra ordenar tudo de uma vez e pergunto se a estrutura BufferedWriter e BufferedReader são o mais recomendado mesmo pra ordenação de blocos do arquivo? é a famosa ordenação que é 1externa mesmo usando alguns algoritmos proprios ,sempre eles ordenam em blocos e estou com duvida em qual estrutura usar pra esses “blocos”
V
vinciPJ
Se você for usar o MergeSort acho que ao invés de usar o BufferedReader você deveria criar um array de 1024 bytes, por exemplo, lê-lo todo de uma vez.
Exemplo:
reader.read(array);
Logo após, você ordenaria o array. Repare que esse array funciona como um buffer manual.
H
HumbertoJrPJ
:eek: Cara ,testei aqui e realmente não levou esse tempo não…tem certeza que tu mudou o conteudo da variavel “tam” pra gerar 500Megabytes em 2 min? Porque creio que 1 Giga tem 1024 Megas,1 mEGA TEM 1024 BYTES …portanto 1Giga tem 1024x1024 bytes,metade disso(500 Megas)é que será o valor de “tam”
Aqui não esta gerando em 2 min não…
Outra duvida que eu tenho ,é sobre teu conselho ,no codigo acima ,“reader” é BufferedReader?
Valeu!
V
vinciPJ
Cara, eu tenho certeza do que estou falando. Copie exatamente o código abaixo e execute.
importjava.io.BufferedWriter;importjava.io.File;importjava.io.FileWriter;importjava.io.IOException;publicclassArquivo{inttamanho;publicArquivo(inttam){tamanho=tam;}publicvoidinicializa(){try{Filefile=newFile("data.txt");FileWriterarquivo=newFileWriter(file);BufferedWriterbuffer=newBufferedWriter(arquivo,1024);for(intcount=0;count<tamanho;count++){buffer.write((char)(65+Math.random()*26));}buffer.flush();buffer.close();System.out.println("Foi gerado "+count+" Bytes e tamanho eh "+file.length());}catch(IOExceptionie){ie.printStackTrace();}}publicstaticvoidmain(Stringargs[]){// tamanho do arquivointt=512*1024*1024;Arquivoa=newArquivo(t);System.out.println("SISTEMA INICIADO");longinicio=System.currentTimeMillis();a.inicializa();longfim=System.currentTimeMillis();longtotal=(fim-inicio)/1000;System.out.println("SISTEMA FINALIZADO EM "+total+" segundos");}}
Numa máquina AMD Sempron 2800 (2GHz), 512 de RAM, em Windows XP, a saída foi:
SISTEMA INICIADO
Foi gerado 536870912 Bytes e tamanho eh 536870912
SISTEMA FINALIZADO EM 107 segundos