[C#] - probleme avec round ?

Bonjour Messieurs,

J’ai un probleme super zarbe.
En C#, je fais un Math.round(variable,2), et je continue a avoir 200 chiffres apres la virgule …

Pour etre sur de rien raté, j’ai blindé de Math.round (du coup c’est pas pertinent, mais c’etait pour etre sur) :

[code] public bool FormatAbbaccusInformation(DataRow dr, out double currentPan, out double currentSC, out double currentDays, out double currentHours)
{
currentPan = -1;
currentSC = -1;
currentDays = -1;
currentHours = -1;

		// On essaie de lire le PAN
		try
		{
			currentPan = (Double)dr["pan"];
		}
		catch
		{
			// on y arrive pas, on quitte en disant que les resultats de cette ligne sont non exploitable en renvoyant false
			//System.Console.WriteLine("Ligne [" + dr..ToString() + "] -- PAN Invalide");
			return (false);
		}


		// On essaie de lire le nombre de jour.
		try
		{
			currentDays = Math.Round((Double)dr["days"],2);
			currentHours = Math.Round(currentDays * 7.5,2);
		}
		catch
		{
			// on y arrive pas, on va tenter de voir si c'est pas parce que la colonne heure est presente
			//System.Console.WriteLine("Ligne [" + dr.ToString() + "] -- Days Invalide");
			// On essaie de lire le nombre d'heure.
			try
			{
				currentHours = Math.Round((Double)dr["hours"],2);
				currentDays = Math.Round(currentHours / 7.5,2);
			}
			catch
			{
				// on y arrive pas, pas de charge associé
				currentHours = -1;
				currentDays = -1;
				return (false);
			}
		}

		// On essaie de lire le Service Code
		try
		{
			currentSC = (Double)dr["service code"];
		}
		catch
		{
			// On y arrive pas, on le mets dans les "unknown service code"
			//System.Console.WriteLine("Ligne [" + dr.ToString() + "] -- Service code Invalide");
		}

		// on a un pan de valide, et une charge valide. Si le sc est invalide il est à -1, sinon il a la bonne valeur
		// on sort en succes
		System.Console.WriteLine("Ligne [" + dr.ToString() + "] -- Succes -- [" + currentPan + "/" + currentSC + "/" + currentDays + "/" + currentHours + "]");
		return (true);
	}[/code]

Mes variables sont des doubles.
Lorsque l’on passe ici, le round semble bien marcher, car le System.Console.WriteLine me sort bien des nombres avec 2 chiffres apres la virgule.
Par contre, quand j’utilise plus loin currentHours et currentDays dans une datatable, j’en ai certain avec plein de chiffre apres la virgule (cf screenshot).

Comment ca se fait ??
Normalement, apres le round, il devrait resté sur 2 chiffres non ?

Comment faire pour etre sur que l’arrondi est bon ?

Au hasard comme ca, le passage dans le DataTable il en profite pas pour refaire une conversion tout seul comme un grand et te niquer ton Round précédent ?

Possible, mais je comprends pas pourquoi : la variable est ecrasée par le contenu du round, donc normalement, il ne devrait plus rien avoir que des 0 apres les deux premiers digits.

Toujours forcer l’arrondi à l’affichage avec des données de type float ou double. Sinon utilises des Decimal.

Là il te manque un formatstring sur ton DataTable pour forcer l’affichage sur 2 décimales uniquement.

Et comment tu utilises ca ?

C’est une proprieté des colonnes ? La colonne de mon datatable est de type Sytem.Double. Comment tu fais pour preciser le nombre de digit à l’affichage ?

Et surtout, pourquoi apres le round à 2 digit, mon double contient des valeurs non nulles apres la deuxieme decimale ??

c’est un type, decimal, comme double ou float ou int. C’est fait pour les calculs où tu souhaites conserver une précision sur les décimales (typiquement les valeurs monétaires).

C’est ta GridView qu’il faut changer, j’ai dit une connerie en parlant de DataTable (ta valeur restera stockée en mémoire avec ces valeurs aproximatives, par contre à l’affichage tu peux lui dire d’arrondir).

Parce qu’un double fonctionne comme un float : il stocke sa valeur en puissances de deux. Donc toutes les fractions ne peuvent pas être représentées, d’où l’approximation. Tu pourras te documenter sur ça sur Wikipedia et sa page sur l’IEEE 754

Et la règle à se souvenir est simple : Si tu veux des chiffres après la virgule non aproximatifs, tu n’utilises pas de float ou double.

On utilise quoi alors ? un decimal ?

Neeed autre chose que float ou double en HLSL, avec un modulo precis :slight_smile: