Erro em saída de dados

Oi pessoal, sou iniciante em java e não consigo entender os erros de saídas num exemplo que fiz.
No caso, o erro é no método de saque da classe Conta. Em alguns valores de entrada o resultado sai errado (imagem abaixo), já em outros sai correto. Alguém aí pode me ajudar e explicar o por quê disso? Valeu!

package exemploConta;
public class Conta {
		
		//declaração das variáveis de objeto, ou atributos. São o "projeto" de uma conta
		public int numero;
		public String cliente;
		public double saldo;
		public double limite;
		
		//definição de métodos de saque e depósito
		boolean saca(double valor){
			if (this.saldo < valor){
			return false;
			}
			
			else{
			this.saldo = this.saldo - valor;
			return true;
			}
		}
		
		void deposita(double valor) {
		this.saldo += valor;
		}
}

package exemploConta;
import java.util.Scanner;

public class Programa {
	
	private static Scanner in;

	public static void main(String[] args) {		
		
		//início a um novo objeto chamado "minhaConta", do tipo Conta
		Conta minhaConta = new Conta();
		
		//carregamento manual de valores nos atributos minhaConta
		minhaConta.numero = 12345;
		minhaConta.cliente = "Amanda";
		minhaConta.saldo = 1000.00;
		minhaConta.limite = 2000.00;
		
		//impressão dos status da conta
		System.out.println("Conta criada com sucesso!");
		System.out.println("Número da Conta: " + minhaConta.numero);
		System.out.println("Cliente: " + minhaConta.cliente);
		System.out.println("Limite: R$ " + minhaConta.limite);
		System.out.println("Saldo atual: R$ " + minhaConta.saldo);
		System.out.println("**********************");
		
		//leitura de valor para saque
		in = new Scanner(System.in); 
		System.out.println("Digite o valor para saque");
		double valorsaque = in.nextDouble();		
		
		//invocação de método saque
		minhaConta.saca(valorsaque);
		if (minhaConta.saca(valorsaque)){
			System.out.println("Saque efetuado com sucesso. Seu novo saldo é: R$" + minhaConta.saldo);
		}
		else{
			System.out.println("Não é possível efetuar o saque. Seu saldo atual é: R$" + minhaConta.saldo);
		}
			
		//leitura de valor para depósito
		System.out.println("********************");
		System.out.println("Digite o valor para depósito");
		double valordeposito = in.nextDouble();		
		
		//invocação de método depósito
		minhaConta.deposita(valordeposito);
		System.out.println("Novo saldo após depósito: " + minhaConta.saldo);
	
	}
}

Opa tente utilizar o BigDecimal ao invés de utilizar o double, tanto a primitiva double quanto a Classe Double utilizam base binária para cálculo, o que isso significa? que em determinados valores você não terá a resposta correta, daí entra a classe BigDecimal, veja alguns métodos dessa class.

`

class … {
public static void main(String[] args) {
System.out.println(“Subtrai”);
System.out.println(new BigDecimal(“2.00”).subtract(new BigDecimal(“1.1”)));

           System.out.println("");
           System.out.println("Soma");
           System.out.println(new BigDecimal("2.00").add(new BigDecimal("1.2")));

           System.out.println("");
           System.out.println("Compara");
           System.out.println(new BigDecimal("2.00").compareTo(new BigDecimal("1.3")));

           System.out.println("");
           System.out.println("Divide");
           System.out.println(new BigDecimal("2.00").divide(new BigDecimal("2.00")));

           System.out.println("");
           System.out.println("Máximo");
           System.out.println(new BigDecimal("2.00").max(new BigDecimal("1.5")));

           System.out.println("");
           System.out.println("Mínimo");
           System.out.println(new BigDecimal("2.00").min(new BigDecimal("1.6")));

           System.out.println("");
           System.out.println("Potência");
           System.out.println(new BigDecimal("2.00").pow(2));

           System.out.println("");
           System.out.println("Multiplica");
           System.out.println(new BigDecimal("2.00").multiply(new BigDecimal("1.8")));

     }

… }

`
suas operações tem valores sempre exatos pois ao invés da double e Double ela trabalha com base Decimal.

1 curtida

vc efetuou o saque duas vezes, por isso vc tinha 1000, sacou 500 e depois, dentro do if, sacou mais 500.

agora vc deveria evitar utilizar os atributos publicos, inicie os valores no construtor e crie getters para expor esses valores.

2 curtidas

Para quem está a aprender, o BigDecimal só vai complicar. O problema dela é bem mais simples.[quote=“amanda16, post:1, topic:335571”]
//invocação de método saque
minhaConta.saca(valorsaque);
if (minhaConta.saca(valorsaque)){
[/quote]
Estás a sacar duas vezes o valor. Daí que, no teu exemplo, ao sacares 500 estás na verdade a sacar 1000. Para funcionar como pretendes basta remover a linha de saque antes do if, uma vez que dentro do if já fazes o saque.

1 curtida

realmente nem parei para olhar a lógica, você está correto mas se tratando de valores monetários é bom desde já ela começar a esquecer double :slight_smile:

1 curtida

Realmente gnt, chamei o método duas vezes e nem me liguei… Foi isso msm, valeu! :+1:
Blz, vou dar uma olhada melhor nessa classe BigDecimal pra usar tbm.

É, de início tô me baseando nos exemplos da apostila. Vou entrar na parte de construtor agora
valeu! :+1: