GUJ Discussões   :   últimos tópicos   |   categorias   |   GUJ Respostas

[SOLUCIONADO] Somar valores de um array retirado de uma lista txt

Precisei fazer um código onde recebia uma lista externa com Nome do item, quantidade do item e valor do item para depois disso, multiplicar a quantidade com o valor de unidade e somar o valor total dessa lista de compras. Consegui ler a lista e separar cada dado em um array, mas não estou conseguindo salvar esses valores para realizar a soma, não sei se armazenei os dados de forma errada ou não estou sabendo fazer captura desses valores.

Segue a classe:

[code/]
void lerArquivo() throws IOException{
String linha;
try{
//Recebe arquivo txt
FileInputStream arquivo = new FileInputStream(“listadeitens.txt”);
InputStreamReader input = new InputStreamReader(arquivo);
BufferedReader br = new BufferedReader(input);

          do{
                linha = br.readLine();
                int totalItem;
                if (linha != null){
                
                   
                 String[] palavras = linha.split(";");// separa valores entre ";"
                 this.setItens(palavras[0]);
                 this.setQuantItens(Integer.parseInt(palavras[1]));
                 this.setValorItem(Integer.parseInt(palavras[2]));
                  
                   totalItem = this.getQuantItens()* this.getValorItem()/100;   
                   System.out.println("O valor total do Item "+ this.getItens()+ " é: " + totalItem + " reais.");
                  
                                    
             }
             }while (linha!= null);
          
           }catch(IOException e){
            System.out.println("Erro!");
        }

}[/code]

Esse é o conteúdo do arquivo txt (listadeitens.txt)

Batata;2;250
Feijão;1;350
Queijo;5;1240
Presunto;3;1030
Farinha;1;250

Esse é o retorno que recebo

O valor total do Item Batata é: 5 reais.
O valor total do Item Feijão é: 3 reais.
O valor total do Item Queijo é: 62 reais.
O valor total do Item Presunto é: 30 reais.
O valor total do Item Farinha é: 2 reais.

Para que esta divisão por 100? Os valores lidos estão em centavos?
Se assim for, totalItem não pode ser um int mas terá de ser um double. E, como a divisão de inteiros em java retorna inteiros (divisão inteira, descartando o resto), não podes dividir por 100 mas sim por 100.0

Sim, fiz a divisão porque o retorno precisa ser em reais e o valor registrado em centavos.

Mas eu preciso mesmo é somar todos os valores após a multiplicação das quantidades.

Quando crio uma variavel dentro do while para salvar os valores ela repete a mesma coisa várias vezes e não soma.

Para a soma de todos os valores, tens de inicializar a variavel com 0 antes do while e ir depois somando o valor da soma por item.

int somaTotal = 0;

do {
   ...
   totalItem = this.getQuantItens()* this.getValorItem()/100;  
   System.out.println("O valor total do Item "+ this.getItens()+ " é: " + totalItem + " reais.");
   somaTotal += totalItem;
   (...)
} while (linha!= null);

System.out.println("O valor total da compra é " + somaTotal + " reais.");

Você não colocou o código dos métodos setItens, getItens e demais getters e setters, mas eu acho que nem precisa disso. Se você só precisa imprimir os valores de cada item, não precisa guardá-los, pode simplesmente imprimir e pronto.

Para o total, basta ter outra variável que guarda o valor total de todos os itens.

Para abrir o arquivo, a partir do Java 7 você pode usar o try-with-resources, que garante que o arquivo é fechado ao final (mesmo em caso de erro).

Enfim, poderia ser assim:

try (BufferedReader reader = new BufferedReader(new FileReader("listadeitens.txt"))) {
    int total = 0; // total geral (todos os itens)
    String linha;
    while ((linha = reader.readLine()) != null) {
        String[] partes = linha.split(";");
        String item = partes[0];
        // calcula o valor total do item
        int qtd = Integer.parseInt(partes[1]);
        int valor = Integer.parseInt(partes[2]);
        int totalItem = qtd * valor;
        System.out.printf("O valor total do item %s é %.2f reais\n", item, totalItem / 100.0);
        // soma ao total geral
        total += totalItem;
    }
    System.out.printf("O valor total da compra é %.2f reais\n", total / 100.0);
} catch (IOException e) {
    // tratar o erro, mostrar mensagem, etc
}

E para imprimir os valores, usei printf juntamente com o formato %.2f, que imprime o número com duas casas decimais.


Se bem que para valores monetários seria melhor usar um java.text.NumberFormat, pois ele já possui uma forma pronta de formatar dinheiro:

// locale pt-BR é Português Brasileiro, então ele já usa R$ como a moeda
NumberFormat formatter = NumberFormat.getCurrencyInstance(new Locale("pt", "BR"));
try (BufferedReader reader = new BufferedReader(new FileReader("listadeitens.txt"))) {
    int total = 0; // total geral (todos os itens)
    String linha;
    while ((linha = reader.readLine()) != null) {
        String[] partes = linha.split(";");
        String item = partes[0];
        // calcula o valor total do item
        int qtd = Integer.parseInt(partes[1]);
        int valor = Integer.parseInt(partes[2]);
        int totalItem = qtd * valor;
        System.out.printf("O valor total do item %s é %s\n", item, formatter.format(totalItem / 100.0));
        // soma ao total geral
        total += totalItem;
    }
    System.out.printf("O valor total da compra é %s\n", formatter.format(total / 100.0));
} catch (IOException e) {
    // tratar o erro, mostrar mensagem, etc
}

A saída será um pouco diferente, pois o NumberFormat inclui o prefixo “R$”:

O valor total do item Batata é R$ 5,00
O valor total do item Feijão é R$ 3,50
O valor total do item Queijo é R$ 62,00
O valor total do item Presunto é R$ 30,90
O valor total do item Farinha é R$ 2,50
O valor total da compra é R$ 103,90

Eu tinha feito os Getters e Setter sim, acabei esquecendo de mostrar aqui. Implementei o que você disse e funcionou, ele está mostrando o total da lista, mas ainda tinha uma segunda parte onde eu preciso pegar esse valor e dividir conforme a quantidade de linhas de outro arquivo txt, mas não estou conseguindo extrair esse valor para usar fora do metodo.
Assim ficou o meu código da soma:

import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;

public class ListaCompras {

String itens; //Recebe nome dos itens
int quantItens; // Recebe quantidade de itens
int valorItem;  //Recebe valor da unidade


void tratarArquivo() throws FileNotFoundException,IOException{
      
        try(BufferedReader reader = new BufferedReader(new FileReader("listadeitens.txt"))) {
           int total = 0; // total geral (todos os itens)
           String linha; 
           while((linha = reader.readLine()) != null){
               String[] partes = linha.split(";");
               String item = partes [0];
               this.setQuantItens(Integer.parseInt(partes[1]));
               this.setValorItem(Integer.parseInt(partes[2]));
               int totalItem =  this.getQuantItens()* this.getValorItem();
               
               //Exibe os itens com as quantidades calculadas
               System.out.printf("O valor total do item %s é %.2f reais\n", item, totalItem / 100.0);
             
                total += totalItem;//realiza a soma de todos os itens com as quantidades calculadas
             }
              //Exibe o valor total da compra
              System.out.printf("O valor total da compra é %.2f reais\n", total / 100.0); 
              
           }catch(IOException e){
            System.out.println("Erro!");
        }

}

public String getItens() {
    return itens;
}

public void setItens(String itens) {
    this.itens = itens;
}

public int getQuantItens() {
    return quantItens;
}

public void setQuantItens(int quantItens) {
    this.quantItens = quantItens;
}

public int getValorItem() {
    return valorItem;
}

public void setValorItem(int valorItem) {
    this.valorItem = valorItem;
}

}

Essa é a outra classe que fiz para ler a outra lista

import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;

public class ListaNomes{

String nomeCliente;


void LerCliente() throws FileNotFoundException, IOException{
    
    try(BufferedReader reader = new BufferedReader(new FileReader("listadecliente.txt"))) {
   
        while((nomeCliente = reader.readLine()) != null){
        
      System.out.println(nomeCliente);
       
       }
    }catch(IOException e){
            System.out.println("Erro!");
    }
}

}

Na saída aparece primeiro o total e depois aparece a lista de Clientes.
Resumindo: Preciso que na saída apareça uma lista com o nome dos Clientes e o valor total divido entre as quantidades de nomes dessa lista.
Eu tentei fazer um método para isso, mas não consegui capturar o valor do método tratarArquivos().

Bom, eu acho que esses getters e setters são desnecessários.

Enfim, para ler e guardar os nomes dos clientes, use uma lista:

List<String> clientes = new ArrayList<>();
try (BufferedReader reader = new BufferedReader(new FileReader("listadeclientes.txt"))) {
    String linha;
    while ((linha = reader.readLine()) != null) {
        clientes.add(linha);
    }
}

Para imprimir os nomes:

System.out.println("nomes dos clientes");
for(String nome: clientes) {
    System.out.println("- " + nome);
}

E para pegar a quantidade de clientes, use clientes.size() (não entendi bem como é pra usar isso, mas enfim, basta usar o size onde você precisar).

Consegui capturar o tamanho da lista na classe LerCliente() depois da sua dica, mas agora eu precisava pegar esse valor e dividir pelo valor total da lista de compras da classe tratarArquivo() para mostrar na tela as duas informações juntas de cada cliente

No final precisa aparecer na tela seria mais ou menos assim:

O cliente [nome do cliente] deverá pagar R$ [valor total da lista/quantidade de clientes]
O cliente [nome do cliente] deverá pagar R$ [valor total da lista/quantidade de clientes]
O cliente [nome do cliente] deverá pagar R$ [valor total da lista/quantidade de clientes]

Como um dicionário/mapa.

O cliente Carlos deverá pagar R$ 30,00.
O cliente Marcos deverá pagar R$30,00.
O cliente José deverá pagar R$30,00.

Não é só pegar o total (que já foi calculado aqui) e dividir pelo tamanho da lista (clientes.size())?

Sim, é que eu não estou conseguindo usar o valor da variável total fora dessa classe. Tipo unir essas duas informações. Não sei se por uma terceira classe ou algum outro tipo de código.

Me desculpa, tem muito tempo que não programo nada e pode ser algo simples que não estou conseguindo ver.

Estou revisando o código novamente para tentar captar essa forma de fazer.

Mas por que precisa ser em duas classes? Eu acho que não precisa (a não ser que seja “exigência” do exercício).

Se precisar mesmo, então o jeito é fazer o total ser uma variável de instância e criar um getter para ela…

Eu fiquei tão presa com duas classes, mas vou tentar unir as duas então.

Juntei as duas classes e deu certo.

Realizei a divisão e desenvolvi a lista conforme sua indicação. Muito obrigada!! Me salvou!

//