Ir ao conteúdo

Posts recomendados

Postado

Sou iniciante em programação em C e estou com uma duvida nesse código, ele basicamente calcula a menor quantidade de moedas que serão utilizadas para dar troco ao usuário, o código tá funcionando e tal, mas ele sempre deixa um resto de 0.01 que é correspondente a 1 centavo e eu não sei como fazer com que ele não deixe mais esse resto.

Se alguém souber como fazer isso por favor me ajudem.

 

#include <cc50.h>
#include <stdio.h>
#include <stdlib.h>

int
main(void)
{
	//Pergunta ao usuario o troco que ele tem que receber
	printf("quanto de troco você quer receber? \n");
	float troco = GetFloat();
	//variavel usada no While
	int fim = 1;
	//contador de quantas moedas vão ser necessarias
	int contador = 0;
	
	// Loop que vai calcular a menor quantidade de moedas para o troco do cliente
	do
	{
	if(troco >= 0.25){
	contador++;
	troco = troco - 0.25;

	} else if (troco >= 0.10){
	contador++;
	troco = troco - 0.10;

	} else if (troco >= 0.05){
	contador++;
	troco = troco - 0.05;
	
	} else if (troco >= 0.010){
	contador++;
	troco = troco - 0.01;

	} else{
	fim = 0;
	}
}
	while(fim == 1);
	
	//imprimi a quantidade de moedas que o while calculou
	printf("%d\n",contador);
	
}

 

cc50_c_library.zip

  • Amei 1
Postado

@Arthur_Azvd @Arthur_Azvd    não sei por quê , mais seu código não está funcionando !  ,  e creio que seja aquela atribuição no final que esteja causando esse erro , e então seu código com algumas modificações poderia ser assim  :

//#include <cc50.h> //  esse aqui não se encontra nesse código , por isso não funciona não
#include <stdio.h>
#include <stdlib.h>
int main(){ // não precisa colocar esse Void não
    float troco;  // criei essa variável depois
	//Pergunta ao usuario o troco que ele tem que receber
	printf("quanto de troco você quer receber? \n");
	//float troco = GetFloat();
	scanf("%f",&troco);
	//variavel usada no While
	int fim = 1;
	//contador de quantas moedas vão ser necessarias
	int contador = 0;
	// Loop que vai calcular a menor quantidade de moedas para o troco do cliente
	do{
        if(troco >= 0.25){
            contador++;
            troco = troco - 0.25;
        }
        else  // não existe ElseIf na linguagem c
            if(troco >= 0.10){// só existe o Else  e o  If
	            contador++;
	            troco = troco - 0.10;
	        }
            else
                if( troco >= 0.05 ){
                    contador++;
                    troco = troco - 0.05;
                }
                else
                    if( troco >= 0.010 ){
                        contador++;
                        troco = troco - 0.01;// aqui pode ser a causa de sempre deixar 0,01
                    }
                    else{
                        fim = 0;
                    }
    }
	while(fim == 1);// esse comoando aqui é Demais , pois ele não fará nada ?
	//imprimi a quantidade de moedas que o while calculou
	printf("%d\n",contador);
	return 32768;  //  geralmente retorna alguma coisa pois a função é int main
}

 

  • Obrigado 1
Postado

Use centavos como unidade e não como 0.01 e calcule tudo usando int. 

 

Usar float e double sempre inclui um risco de erro de arredondamento e sobra algo. E quando compara muitas vezes não dá igual porque na representação interna de dois float eles podem diferir por algum valor lá na oitava casa decimal por exemplo, devido à representação não ser exata.

 

Por isso COBOL foi a linguagem do dinheiro por décadas: contas sem erro de arredondamento.

  • Curtir 1
  • Obrigado 1
Postado

@Arthur_Azvd Usou uma função dessa tal biblioteca cc50.h só pra ler um float? Não é mais fácil só usar scanf(), e declarar uma variável no mínimo do tipo double ao invés de float? Com double a precisão é maior, mas você ainda pode ter problemas com isso, não é bom trabalhar com números tão pequenos.

Não esqueça de incluir a biblioteca locale.h para possibilitar imprimir acentuação. Indentação também é importante.

 

Teste isso:

#include <stdio.h>
#include <locale.h>

int main()
{
    setlocale(LC_ALL, "Portuguese");
    long double troco;
    //Pergunta ao usuario o troco que ele tem que receber
    printf("quanto de troco você quer receber? \n");
    scanf("%Lf", &troco);
    //variavel usada no While
    int fim = 1;
    //contador de quantas moedas vão ser necessarias
    int contador = 0;
	
    // Loop que vai calcular a menor quantidade de moedas para o troco do cliente
    do{
    	if(troco >= 0.25){
    	    contador++;
    	    troco -= 0.25;
    	}else if (troco < 0.25 && troco >= 0.1){
    	    contador++;
    	    troco -= 0.10;
    	}else if (troco < 0.10 && troco >= 0.05){
    	    contador++;
    	    troco -= 0.05;
    	}else if (troco < 0.05 && troco >= 0.009){
    	    contador++;
    	    troco -= 0.01;
    	}else{
    	    fim = 0;
    	}
    }while(fim == 1);
	
    //imprimi a quantidade de moedas que o while calculou
    printf("%d\n",contador);
	
}

 

  • Obrigado 2
Postado

O seu código está comparando `floats` com `doubles` literais, o que não é recomendado. O compilador pode até resolver isso para você, mas o padrão é que o `double` literal seja convertido implicitamente, truncando o valor representado e causando um erro de arredondamento minúsculo que se acumula com as múltiplas operações realizadas. Se o `double` está disponível, faça os cálculos e comparações todos em `double`, apesar que comparações de igualdade tipicamente não funcionam como esperado em ponto flutuante binário.

 

Cálculo com ponto flutuante binário e erros de arredondamento andam juntos e são esperados, mas isso não é o caso em se tratando de dinheiro. Há alguns processadores que suportam ponto flutuante decimal em hardware, mas a estratégia mais comum que já vi envolve usar inteiros com ou sem sinal e escalas (acho que a classe `BigDecimal` do Java funciona assim). Se o problema não envolvesse decimais e aceitasse binários, poderia usar, isto é, implementar, em ponto fixo, já que o suporte no compilador é uma extensão do GCC não compatível com todas as arquiteturas.

 

Leitura interessante:
https://randomascii.wordpress.com/2012/02/25/comparing-floating-point-numbers-2012-edition/

Versão longa e muito mais detalhada (até hoje não terminei de ler):

https://docs.oracle.com/cd/E19957-01/806-3568/ncg_goldberg.html

  • Curtir 1
  • Obrigado 1
Postado

Imprecisão: Fração Decimal --> Binário

 

Por conta da imprecisão ao representar frações de décimos em binários; conclui-se, por exemplo, que 0.01 é representado não exatamente 1/100; E a propagação dessa imprecisão aumenta na medida das operações ou que no final o valor 0.01 restante na variável é ≅ 0.0099...d

 

  • Curtir 1
  • Obrigado 2

Crie uma conta ou entre para comentar

Você precisa ser um usuário para fazer um comentário

Criar uma conta

Crie uma nova conta em nossa comunidade. É fácil!

Crie uma nova conta

Entrar

Já tem uma conta? Faça o login.

Entrar agora

Sobre o Clube do Hardware

No ar desde 1996, o Clube do Hardware é uma das maiores, mais antigas e mais respeitadas comunidades sobre tecnologia do Brasil. Leia mais

Direitos autorais

Não permitimos a cópia ou reprodução do conteúdo do nosso site, fórum, newsletters e redes sociais, mesmo citando-se a fonte. Leia mais

×
×
  • Criar novo...

LANÇAMENTO!

eletronica2025-popup.jpg


CLIQUE AQUI E BAIXE AGORA MESMO!