소수점 값을 소수점 이하 2 자리로 반올림하는 방법 (페이지 출력)


649

현재 10 진수 값을 표시 할 때 .ToString() 15 자리를 좋아하는 것이 정확하며, 달러와 센트를 나타내는 데 사용하기 때문에 출력은 소수점 2 자리 만 원합니다.

.ToString()이 변형을 사용 합니까?

답변:


911
decimalVar.ToString ("#.##"); // returns "" when decimalVar == 0

또는

decimalVar.ToString ("0.##"); // returns "0"  when decimalVar == 0

31
여기서 문제는 0.00 일 때입니다. 빈 문자열을 반환합니다.
Jronny

164
그런 다음 decimalVar.ToString ( "0. ##")을 수행 할 수 있습니다. 서식 문자열로 0.00을 사용할 수도 있습니다.
albertein

54
이 솔루션을 사용하면 숫자를 읽을 때 예상되는 문화 형식이 없습니다. 이를 위해 ToString ( "N2") 또는 ToString ( "N")을 사용해야합니다.
Shautieh

2
@Hill DecimalDoubletype ToString메소드는 형식화를위한 인수를 허용합니다. 먼저 값을 10 진수 / 더블로 변환 해보십시오.
sohaiby

1
@ f470071 10 진수는 값 유형이므로 "수정"되지 않습니다. 그럼에도 불구하고 ToString ()은 호출 된 내용을 수정하지 않습니다.
저스틴 스키 레스

590

나는 이것이 오래된 질문이라는 것을 알고 있지만 아무도 그 답을 올리지 않는 것 같았다.

  1. 은행 반올림을 사용하지 않았습니다
  2. 값을 10 진수로 유지하지 않았습니다.

이것이 내가 사용하는 것입니다 :

decimal.Round(yourValue, 2, MidpointRounding.AwayFromZero);

http://msdn.microsoft.com/en-us/library/9s0xa85y.aspx


3
ToString 또는 string.Format은 뱅커 반올림을 사용하지 않습니다. msdn.microsoft.com/en-us/library/0c899ak8.aspx#sectionToggle1
Matthijs Wessels

1
@MatthijsWessels 알고 있습니다 ...하지만 값을 소수점으로 유지하지는 않습니다.
Mike M.

1
후행 0을 제거하지 않으므로 소수점 이하 두 자리를 실제로 나타내는 더 좋은 방법입니다.
LiquidDrummer

355
decimalVar.ToString("F");

이것은 :

  • 소수점 이하 두 자리로 반올림합니다 ( 예 : 23.45623.46
  • 소수점 이하 두 자리가 항상 있는지 확인하십시오 ( 예 : 2323.00; 12.512.50

통화 표시에 이상적입니다.

ToString ( "F") 에 대한 문서를 확인하십시오 (Jon Schneider 덕분에).


10
소수점 이하 1 자리 일 때 잘 작동합니다. .ToString ( "#. ##")이 실패합니다. 이 답변은 훨씬 좋습니다
Eric Frick

2
23.456 => 23.46이 아닌가?
rtpHarry

14
"F"의 의미 및 작동 방식에 대한 설명서 : msdn.microsoft.com/en-us/library/…
Jon Schneider

4
"F"대신 .ToString ( "N")이 아닌 이유는 무엇입니까? 그들이이 질문의 요구에 모두 작동한다는 것을 이해하지만 N은 수천의 숫자에 쉼표를 넣을 것입니다.
jgerman

참고 : 문화권에 따라 이로 .대체 될 수 있습니다 ,. CultureInfo.InvariantCulture이를 비활성화하려면 두 번째 인수로 전달해야 합니다.
Duncan Luk

106

표시를 위해 이것을 필요로하는 경우 string을 사용하십시오.

String.Format("{0:0.00}", 123.4567m);      // "123.46"

http://www.csharp-examples.net/string-format-double/

"m"은 10 진수 접미사입니다. 소수 접미사 정보 :

http://msdn.microsoft.com/en-us/library/364x0z75.aspx


10
기술적으로, 십진수의 경우 123.4567m입니다. "m"접미사가 없으면 두 배입니다
Adam Tegen

2
또는 바로 가기 $ "{value : 0.00}"
mamczas

56

주어진 10 진수 d = 12.345; d.ToString ( "C") 또는 String.Format ( "{0 : C}", d) 표현식 은 $ 12.35입니다. .-기호를 포함한 현재 문화권의 통화 설정이 사용됩니다.

참고 "C" 현재 문화권에서 숫자의 사용 번호. C{Precision specifier}like로 필요한 정밀도를 강제하기 위해 항상 기본값을 무시할 수 있습니다 String.Format("{0:C2}", 5.123d).


4
@ Slick86-현재의 표시
fubo

48

3,456,789.12와 같이 소수점과 통화 기호가 아닌 쉼표로 형식을 지정하려면 ...

decimalVar.ToString("n2");

1
질문이 페이지에 출력되는 것에 대한 질문에 대한 더 나은 대답이며 숫자 형식은 큰 숫자에 중요합니다. 또한 "n *"는 현재 문화를 고려하므로 "3.456.789,12", "3 456 789,12"등이 될 수 있습니다.
Shautieh

29

Decimal.Round (...)를 참조하는 두 개의 높은 점수 답변이 이미 있지만 조금 더 설명이 필요하다고 생각합니다 .Decimal의 예기치 않은 중요한 속성이 분명하지 않기 때문입니다.

십진수는 어디서 왔는지에 따라 소수 자릿수가 얼마나 많은지를 '알고'있습니다.

예를 들어 다음은 예상치 못한 결과 일 수 있습니다.

Decimal.Parse("25").ToString()          =>   "25"
Decimal.Parse("25.").ToString()         =>   "25"
Decimal.Parse("25.0").ToString()        =>   "25.0"
Decimal.Parse("25.0000").ToString()     =>   "25.0000"

25m.ToString()                          =>   "25"
25.000m.ToString()                      =>   "25.000"

동일한 작업을 수행하면 위의 각각에 Double소수점 이하 자릿수 ( "25") 가 표시되지 않습니다 .

소수점 이하 2 자리를 원할 때 약 95 % 확률이 있습니다. 통화 인 경우 통화 시간이 95 %에 해당 할 수 있습니다.

Decimal.Parse("25.0").ToString("c")     =>   "$25.00"

또는 XAML에서 그냥 사용하십시오. {Binding Price, StringFormat=c}

XML을 Amazon의 웹 서비스에 보낼 때 10 진수로 10 진수가 필요한 경우가 발생했습니다. 10 진수 값 (원래 SQL Server에서 온)이 전송되어 25.1200거부 되어 서비스가 불만을 제기했습니다 (25.12 있었습니다 (예상 형식).

내가해야 할 일은 Decimal.Round(...)문제를 해결하기 위해 소수점 이하 2 자리를 사용하는 것입니다.

 // This is an XML message - with generated code by XSD.exe
 StandardPrice = new OverrideCurrencyAmount()
 {
       TypedValue = Decimal.Round(product.StandardPrice, 2),
       currency = "USD"
 }

TypedValue유형이 Decimal있으므로 그냥 할 수 없었고 ToString("N2")반올림하고로 유지해야했습니다 decimal.


5
+1 이것은 훌륭한 답변입니다. System.Decimal이 "소수 자릿수를 알고 있음"이라고 말하면 System.Decimal은 다른 부동 소수점 유형처럼 자체 정규화 되지 않습니다 . System.Decimal의 또 다른 유용한 속성은 수학 연산의 결과가 항상 입력 인수에서 가장 높은 소수 자릿수를 갖는다는 것입니다. 1.0m + 2.000m = 3.000m 입니다. 예를 들어,이 사실을 사용하면 소수점 이하 자릿수가없는 소수점 이하 자릿수에 간단히 1.00m을 곱하여 소수점 이하 두 자리까지 강제 할 수 있습니다. 10m * 1.00m = 10.00m 입니다.
MattDavey

2
MattDavey의 값이 올바르지 않습니다. 10 진 정밀도가 추가됩니다. (1.0m * 1.00m) .ToString () = "1.000"
Kaido

2
"소수점은 소수점 위치가 얼마나 많은지를 '알고 있습니다'"라는 사실을 아는 것이 매우 유용합니다. 고마워요!
iheartcsharp

21

다른 형식을 보여주는 작은 Linqpad 프로그램은 다음과 같습니다.

void Main()
{
    FormatDecimal(2345.94742M);
    FormatDecimal(43M);
    FormatDecimal(0M);
    FormatDecimal(0.007M);
}

public void FormatDecimal(decimal val)
{
    Console.WriteLine("ToString: {0}", val);
    Console.WriteLine("c: {0:c}", val);
    Console.WriteLine("0.00: {0:0.00}", val);
    Console.WriteLine("0.##: {0:0.##}", val);
    Console.WriteLine("===================");
}

결과는 다음과 같습니다.

ToString: 2345.94742
c: $2,345.95
0.00: 2345.95
0.##: 2345.95
===================
ToString: 43
c: $43.00
0.00: 43.00
0.##: 43
===================
ToString: 0
c: $0.00
0.00: 0.00
0.##: 0
===================
ToString: 0.007
c: $0.01
0.00: 0.01
0.##: 0.01
===================


11

값이 0이면 빈 문자열을 거의 사용하지 않을 것입니다.

decimal test = 5.00;
test.ToString("0.00");  //"5.00"
decimal? test2 = 5.05;
test2.ToString("0.00");  //"5.05"
decimal? test3 = 0;
test3.ToString("0.00");  //"0.00"

최고 평점 답변이 정확하지 않으며 10 분 동안 (대부분의) 사람들의 시간을 낭비했습니다.


1
기본적으로 "#"숫자의 자릿수 (필요한 경우 패딩 없음)를 "0"의미 합니다 (필요하지 않은 경우 패딩 없음) (사용할 수없는 경우 0으로
채워짐

10

Mike M.의 대답 은 .NET에서 나에게 완벽했지만 .NET Core에는 decimal.Round글을 쓰는 시점에 방법 이 없습니다 .

.NET Core에서는 다음을 사용해야했습니다.

decimal roundedValue = Math.Round(rawNumber, 2, MidpointRounding.AwayFromZero);

문자열로의 변환을 포함한 해키 방법은 다음과 같습니다.

public string FormatTo2Dp(decimal myNumber)
{
    // Use schoolboy rounding, not bankers.
    myNumber = Math.Round(myNumber, 2, MidpointRounding.AwayFromZero);

    return string.Format("{0:0.00}", myNumber);
}

9

이 중 2 dp 를 강제 하고 다음과 같이 반올림하기 위해 내가 필요한 것을 정확하게 수행하지 못했습니다.0.005 -> 0.01

2dp를 강제하면 최소 2dp를 갖기 위해 정밀도를 2dp 씩 증가시켜야합니다.

그런 다음 반올림하여 2dp를 초과하지 않도록합니다.

Math.Round(exactResult * 1.00m, 2, MidpointRounding.AwayFromZero)

6.665m.ToString() -> "6.67"

6.6m.ToString() -> "6.60"

9

최상위 답변은 문자열 표현의 형식을 지정하는 방법을 설명합니다 은 십진수 값 작동합니다.

그러나 실제로 저장된 정밀도를 실제 값으로 변경하려면 다음과 같이 작성해야합니다.

public static class PrecisionHelper
{
    public static decimal TwoDecimalPlaces(this decimal value)
    {
        // These first lines eliminate all digits past two places.
        var timesHundred = (int) (value * 100);
        var removeZeroes = timesHundred / 100m;

        // In this implementation, I don't want to alter the underlying
        // value.  As such, if it needs greater precision to stay unaltered,
        // I return it.
        if (removeZeroes != value)
            return value;

        // Addition and subtraction can reliably change precision.  
        // For two decimal values A and B, (A + B) will have at least as 
        // many digits past the decimal point as A or B.
        return removeZeroes + 0.01m - 0.01m;
    }
}

단위 테스트 예 :

[Test]
public void PrecisionExampleUnitTest()
{
    decimal a = 500m;
    decimal b = 99.99m;
    decimal c = 123.4m;
    decimal d = 10101.1000000m;
    decimal e = 908.7650m

    Assert.That(a.TwoDecimalPlaces().ToString(CultureInfo.InvariantCulture),
        Is.EqualTo("500.00"));

    Assert.That(b.TwoDecimalPlaces().ToString(CultureInfo.InvariantCulture),
        Is.EqualTo("99.99"));

    Assert.That(c.TwoDecimalPlaces().ToString(CultureInfo.InvariantCulture),
        Is.EqualTo("123.40"));

    Assert.That(d.TwoDecimalPlaces().ToString(CultureInfo.InvariantCulture),
        Is.EqualTo("10101.10"));

    // In this particular implementation, values that can't be expressed in
    // two decimal places are unaltered, so this remains as-is.
    Assert.That(e.TwoDecimalPlaces().ToString(CultureInfo.InvariantCulture),
        Is.EqualTo("908.7650"));
}

7

system.globalization을 사용하여 필요한 형식으로 숫자를 형식화 할 수 있습니다.

예를 들면 다음과 같습니다.

system.globalization.cultureinfo ci = new system.globalization.cultureinfo("en-ca");

a가 decimal d = 1.2300000있고 소수점 이하 2 자리로 잘라 d.Tostring("F2",ci);내야하는 경우 F2는 소수점 2 자리까지의 문자열 형식이고 ci는 로케일 또는 cultureinfo 인 경우와 같이 인쇄 할 수 있습니다 .

자세한 내용은이 링크를 확인하십시오
http://msdn.microsoft.com/en-us/library/dwhawy9k.aspx


+1이지만 CultureInfo 개체는 소수점 이하 자릿수를 나타내는 데 사용되는 유니 코드 문자에만 영향을줍니다. 예. fr-FR은 마침표 대신 쉼표를 사용합니다. 렌더링 된 소수 자릿수와 관련이 없습니다.
MattDavey

4

https://msdn.microsoft.com/en-us/library/dwhawy9k%28v=vs.110%29.aspx

이 링크는 문제를 처리하는 방법과 자세한 내용을 알고 싶을 때 수행 할 수있는 작업에 대해 자세히 설명합니다. 간단하게하기 위해 원하는 것은

double whateverYouWantToChange = whateverYouWantToChange.ToString("F2");

통화에 대해 원하는 경우 "F2"대신 "C2"를 입력하여 더 쉽게 만들 수 있습니다.



1

소수점 이하 두 자리 만 유지해야하는 경우 (예 : 나머지 소수점 자릿수 모두 잘라 내기) :

decimal val = 3.14789m;
decimal result = Math.Floor(val * 100) / 100; // result = 3.14

소수점 이하 세 자리 만 유지해야하는 경우 :

decimal val = 3.14789m;
decimal result = Math.Floor(val * 1000) / 1000; // result = 3.147
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.