-3

Por qué si introduzco 4,95 me devuelve los 5 centimos y si introduzco 1,95 no me los devuelve?

package ejer30;
import java.util.Scanner;

public class Expendedora {
    private double dinero;
    private static Scanner sc = new Scanner(System.in);

    public void setDinero() {
        dinero=sc.nextDouble();
    }

    public void calculaMonedas() {

        int cont2E=0;
        int cont1E=0;
        int cont50C=0;
        int cont20C=0;
        int cont10C=0;
        int cont5C=0;

        while (dinero>=2) {
            cont2E++;
            dinero=dinero-2;
        }

        while (dinero>=1) {
            cont1E++;
            dinero=dinero-1;
        }

        while (dinero>=0.50) {
            cont50C++;
            dinero=dinero-0.50;
        }

        while (dinero>=0.20) {
            cont20C++;
            dinero=dinero-0.20;
        }

        while (dinero>=0.10) {
            cont10C++;
            dinero=dinero-0.10;
        }

        while (dinero>=0.05) {
            cont5C++;
            dinero=dinero-0.05;
        }
            System.out.println("Monedas de 2€: "+cont2E);
            System.out.println("Monedas de 1€: "+cont1E);
            System.out.println("Monedas de 50 cent: "+cont50C);
            System.out.println("Monedas de 20 cent: "+cont20C);
            System.out.println("Monedas de 10 cent: "+cont10C);
            System.out.println("Monedas de 5 cent: "+cont5C);
    }       

    public static void main(String[] args) {
        Expendedora a = new Expendedora();
        System.out.println("Introduce dinero: ");
        a.setDinero();
        a.calculaMonedas();
    }
}
JohnnyTB
  • 2,592
  • 1
  • 8
  • 17
David
  • 9
  • 4

1 Answers1

0

Como te puse en el enlace marcando esta pregunta como duplicado (¿Por qué mis programas no pueden hacer cálculos aritméticos correctamente?), el tipo float y double no son tipos precisos. Aun cuando dinero tenga un valor de 0.05, puede que internamente, el valor sea mas bien algo como 0.04999999..., lo que haría que la condición dinero>=0.05 devolviera false.

Para evitar estos problemas de precisión con valores monetarios, puedes usar el tipo BigDecimal. Aunque es mas incómodo en su uso, por lo menos es más preciso.

Aquí te dejo un ejemplo de cómo tu código pudiera usar BigDecimal:

public class Expendedora {
    private static final BigDecimal DOS_EUROS = new BigDecimal("2.00");
    private static final BigDecimal UN_EURO = new BigDecimal("1.00");
    private static final BigDecimal CINCUENTA_CENTAVOS = new BigDecimal("0.50");
    private static final BigDecimal VEINTE_CENTAVOS = new BigDecimal("0.20");
    private static final BigDecimal DIEZ_CENTAVOS = new BigDecimal("0.10");
    private static final BigDecimal CINCO_CENTAVOS = new BigDecimal("0.05");

    private BigDecimal dinero;
    private static Scanner sc = new Scanner(System.in);

    public void setDinero() {
        dinero=sc.nextBigDecimal();
    }

    public void calculaMonedas() {
        int cont2E=0;
        int cont1E=0;
        int cont50C=0;
        int cont20C=0;
        int cont10C=0;
        int cont5C=0;

        while (dinero.compareTo(DOS_EUROS) >= 0) {
            cont2E++;
            dinero=dinero.subtract(DOS_EUROS);
        }

        while (dinero.compareTo(UN_EURO) >= 0) {
            cont1E++;
            dinero=dinero.subtract(UN_EURO);
        }

        while (dinero.compareTo(CINCUENTA_CENTAVOS) >= 0) {
            cont50C++;
            dinero=dinero.subtract(CINCUENTA_CENTAVOS);
        }

        while (dinero.compareTo(VEINTE_CENTAVOS) >= 0) {
            cont20C++;
            dinero=dinero.subtract(VEINTE_CENTAVOS);
        }

        while (dinero.compareTo(DIEZ_CENTAVOS) >= 0) {
            cont10C++;
            dinero=dinero.subtract(DIEZ_CENTAVOS);
        }

        while (dinero.compareTo(CINCO_CENTAVOS) >= 0) {
            cont5C++;
            dinero=dinero.subtract(CINCO_CENTAVOS);
        }

        System.out.println("Monedas de 2€: "+cont2E);
        System.out.println("Monedas de 1€: "+cont1E);
        System.out.println("Monedas de 50 cent: "+cont50C);
        System.out.println("Monedas de 20 cent: "+cont20C);
        System.out.println("Monedas de 10 cent: "+cont10C);
        System.out.println("Monedas de 5 cent: "+cont5C);
    }       

    public static void main(String[] args) {
        Expendedora a = new Expendedora();
        System.out.println("Introduce dinero: ");
        a.setDinero();
        a.calculaMonedas();
    }
}
sstan
  • 16,591
  • 2
  • 21
  • 45