Utilisation du format de chaîne pour afficher décimal jusqu'à 2 places ou entier simple

J'ai un champ de prix à afficher qui peut parfois être 100 ou 100.99 ou 100.9, ce que je veux est d'afficher le prix en 2 décimales seulement si les décimales sont entrées pour ce prix, par exemple si son 100 donc il devrait seulement montrer 100 pas 100.00 et si le prix est 100.2 il devrait afficher 100.20 de même pour 100.22 devrait être le même . J'ai googlé et suis tombé sur quelques exemples mais ils ne correspondaient pas exactement à ce que je voulais:

// just two decimal places
String.Format("{0:0.00}", 123.4567);      // "123.46"
String.Format("{0:0.00}", 123.4);         // "123.40"
String.Format("{0:0.00}", 123.0);         // "123.00"
210
demandé sur Cœur 2011-08-05 08:12:20

15 réponses

Une manière inélégante serait:

var my = DoFormat(123.0);

Avec DoFormat étant quelque chose comme:

public static string DoFormat( double myNumber )
{
    var s = string.Format("{0:0.00}", myNumber);

    if ( s.EndsWith("00") )
    {
        return ((int)myNumber).ToString();
    }
    else
    {
        return s;
    }
}

Pas élégant mais travaillant pour moi dans des situations similaires dans certains projets.

122
répondu Uwe Keim 2014-08-08 10:38:10

Désolé de réactiver cette question, mais je n'ai pas trouvé la bonne réponse ici.

Dans le formatage des numéros, vous pouvez utiliser {[2] } comme lieu obligatoire et # comme lieu facultatif.

Donc:

// just two decimal places
String.Format("{0:0.##}", 123.4567);      // "123.46"
String.Format("{0:0.##}", 123.4);         // "123.4"
String.Format("{0:0.##}", 123.0);         // "123"

, Vous pouvez également combiner 0 avec #.

String.Format("{0:0.0#}", 123.4567)       // "123.46"
String.Format("{0:0.0#}", 123.4)          // "123.4"
String.Format("{0:0.0#}", 123.0)          // "123.0"

Pour cette méthode de formatage est toujours utilisé CurrentCulture. Pour certaines Cultures, {[7] } sera remplacé par ,.

380
répondu Gh61 2018-08-28 11:36:48

C'est un cas d'utilisation de nombre flottant de formatage commun.

Malheureusement, toutes les chaînes de format d'une lettre intégrées (par exemple. F, G, N) n'y parviendra pas directement.
Par exemple, num.ToString("F2") affichera toujours 2 décimales comme 123.40.

Vous devrez utiliser 0.## Modèle même il semble un peu verbeux.

Un exemple de code complet:

double a = 123.4567;
double b = 123.40;
double c = 123.00;

string sa = a.ToString("0.##"); // 123.46
string sb = b.ToString("0.##"); // 123.4
string sc = c.ToString("0.##"); // 123
45
répondu detale 2015-10-18 06:13:08

Essayez

double myPrice = 123.0;

String.Format(((Math.Round(myPrice) == myPrice) ? "{0:0}" : "{0:0.00}"), myPrice);
27
répondu Yahia 2011-08-05 04:15:42

Ancienne question mais je voulais ajouter l'option la plus simple à mon avis.

Sans séparateurs de milliers:

value.ToString(value % 1 == 0 ? "F0" : "F2")

Avec séparateurs de milliers:

value.ToString(value % 1 == 0 ? "N0" : "N2")

La même chose mais avec chaîne.Format :

String.Format(value % 1 == 0 ? "{0:F0}" : "{0:F2}", value) // Without thousands separators
String.Format(value % 1 == 0 ? "{0:N0}" : "{0:N2}", value) // With thousands separators

Si vous en avez besoin dans de nombreux endroits, je voudrais utiliser cette logique dans un méthode d'extension:

public static string ToCoolString(this decimal value)
{
    return value.ToString(value % 1 == 0 ? "N0" : "N2"); // Or F0/F2 ;)
}
27
répondu Andrew 2016-07-14 21:57:44

Je ne sais pas de toute façon de mettre une condition dans le spécificateur de format, mais vous pouvez écrire votre propre formateur:

using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Text;

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
               // all of these don't work
            Console.WriteLine("{0:C}", 10);
            Console.WriteLine("{0:00.0}", 10);
            Console.WriteLine("{0:0}", 10);
            Console.WriteLine("{0:0.00}", 10);
            Console.WriteLine("{0:0}", 10.0);
            Console.WriteLine("{0:0}", 10.1);
            Console.WriteLine("{0:0.00}", 10.1);

          // works
            Console.WriteLine(String.Format(new MyFormatter(),"{0:custom}", 9));
            Console.WriteLine(String.Format(new MyFormatter(),"{0:custom}", 9.1));
            Console.ReadKey();
        }
    }

    class MyFormatter : IFormatProvider, ICustomFormatter
    {
        public string Format(string format, object arg, IFormatProvider formatProvider)
        {
            switch (format.ToUpper())
            {
                case "CUSTOM":
                    if (arg is short || arg is int || arg is long)
                        return arg.ToString();
                    if (arg is Single || arg is Double)
                        return String.Format("{0:0.00}",arg);
                    break;
                // Handle other
                default:
                    try
                    {
                        return HandleOtherFormats(format, arg);
                    }
                    catch (FormatException e)
                    {
                        throw new FormatException(String.Format("The format of '{0}' is invalid.", format), e);
                    }
            }
            return arg.ToString(); // only as a last resort
        }

        private string HandleOtherFormats(string format, object arg)
        {
            if (arg is IFormattable)
                return ((IFormattable)arg).ToString(format, CultureInfo.CurrentCulture);
            if (arg != null)
                return arg.ToString();
            return String.Empty;
        }

        public object GetFormat(Type formatType)
        {
            if (formatType == typeof(ICustomFormatter))
                return this;
            return null;
        }
    }
}
7
répondu Tim Hoolihan 2011-08-05 04:36:39

Code simple d'une ligne:

public static string DoFormat(double myNumber)
{
    return string.Format("{0:0.00}", myNumber).Replace(".00","");
}
7
répondu Philip Stuyck 2017-02-17 16:23:31

Voici une alternative à la méthode de Uwe Keim, qui maintiendrait toujours le même appel de méthode:

var example1 = MyCustomFormat(123.1);  // Output: 123.10
var example2 = MyCustomFormat(123.95); // Output: 123.95
var example3 = MyCustomFormat(123);    // Output: 123

Avec MyCustomFormat étant quelque chose comme:

public static string MyCustomFormat( double myNumber )
{
    var str (string.Format("{0:0.00}", myNumber))
    return (str.EndsWith(".00") ? str.Substring(0, strLastIndexOf(".00")) : str;
}
6
répondu Steve 2014-02-07 12:17:47

Je crains qu'il n'y ait pas de format intégré qui le fera. Vous devrez utiliser un format différent selon que la valeur est un nombre entier ou pas. Ou formatez toujours à 2 décimales, et manipulez la chaîne par la suite pour supprimer toute fin ".00".

5
répondu Nikki Locke 2011-08-05 04:15:34

Si aucune des autres réponses ne fonctionne pour vous, c'est peut-être parce que vous liez le ContentProperty d'un contrôle dans la fonction OnLoad, ce qui signifie que cela ne fonctionnera pas:

private void UserControl_Load(object sender, RoutedEventArgs e)
{
  Bind.SetBindingElement(labelName, String.Format("{0:0.00}", PropertyName), Label.ContentProperty) 
}

La solution est simple: il y a une propriété ContentStringFormat dans le xaml. Donc, lorsque vous créez l'étiquette, faites ceci:

//if you want the decimal places definite
<Label Content="0" Name="labelName" ContentStringFormat="0.00"/>

Ou

//if you want the decimal places to be optional
<Label Content="0" Name="labelName" ContentStringFormat="0.##"/>
4
répondu Brazizzle 2015-09-08 22:54:56

Quelque chose comme ça fonctionnera aussi:

String.Format("{0:P}", decimal.Parse(Resellers.Fee)).Replace(".00", "")
3
répondu ekkis 2014-01-12 01:35:37

Chaîne.Format ("{0:0.00}", Convertir.ToDecimal (totalPrice))

3
répondu user1067656 2017-07-24 21:18:32

Pour rendre le code plus clair que Kahia a écrit (c'est clair mais ça devient difficile quand vous voulez ajouter plus de texte)...essayez cette solution simple.

if (Math.Round((decimal)user.CurrentPoints) == user.CurrentPoints)
     ViewBag.MyCurrentPoints = String.Format("Your current Points: {0:0}",user.CurrentPoints);
else
     ViewBag.MyCurrentPoints = String.Format("Your current Points: {0:0.0}",user.CurrentPoints);

J'ai dû ajouter le cast supplémentaire (décimal) pour avoir des mathématiques.Ronde comparer les deux variables décimales.

2
répondu coding_is_fun 2014-02-06 00:27:15

Si votre programme doit s'exécuter rapidement, appelez valeur.ToString (formatString) pour des performances de formatage de chaîne ~35% plus rapides par rapport à $ "{value: formatString} " et string.Format (formatString, valeur).

Données

Performances de formatage de chaîne C# - VS2017 15.4.5

Code

using System;
using System.Diagnostics;

public static class StringFormattingPerformance
{
   public static void Main()
   {
      Console.WriteLine("C# String Formatting Performance");
      Console.WriteLine("Milliseconds Per 1 Million Iterations - Best Of 5");
      long stringInterpolationBestOf5 = Measure1MillionIterationsBestOf5(
          (double randomDouble) =>
          {
             return $"{randomDouble:0.##}";
          });
      long stringDotFormatBestOf5 = Measure1MillionIterationsBestOf5(
          (double randomDouble) =>
          {
             return string.Format("{0:0.##}", randomDouble);
          });
      long valueDotToStringBestOf5 = Measure1MillionIterationsBestOf5(
          (double randomDouble) =>
          {
             return randomDouble.ToString("0.##");
          });
      Console.WriteLine(
$@"            $""{{value:formatString}}"": {stringInterpolationBestOf5} ms
 string.Format(formatString, value): {stringDotFormatBestOf5} ms
       value.ToString(formatString): {valueDotToStringBestOf5} ms");
   }

   private static long Measure1MillionIterationsBestOf5(
       Func<double, string> formatDoubleUpToTwoDecimalPlaces)
   {
      long elapsedMillisecondsBestOf5 = long.MaxValue;
      for (int perfRunIndex = 0; perfRunIndex < 5; ++perfRunIndex)
      {
         var random = new Random();
         var stopwatch = Stopwatch.StartNew();
         for (int i = 0; i < 1000000; ++i)
         {
            double randomDouble = random.NextDouble();
            formatDoubleUpToTwoDecimalPlaces(randomDouble);
         }
         stopwatch.Stop();
         elapsedMillisecondsBestOf5 = Math.Min(
            elapsedMillisecondsBestOf5, stopwatch.ElapsedMilliseconds);
      }
      return elapsedMillisecondsBestOf5;
   }
}

Sortie De Code

C# String Formatting Performance
Milliseconds Per 1 Million Iterations - Best Of 5
            $"{value:formatString}": 419 ms
 string.Format(formatString, value): 419 ms
       value.ToString(formatString): 264 ms

Références

Chaînes de Format numérique personnalisées [docs.microsoft.com]

Qt Graphiques BarChart Exemple [doc.qt.io]

2
répondu Neil Justice 2017-12-03 22:40:02

Cela a fonctionné pour moi!

String amount= "123.0000";
String.Format("{0:0.##}", amount);      // "123.00"
1
répondu Edwin Ikechukwu 2015-03-14 13:08:14