Afskæring af antallet af cifre af dobbelt værdi i C#

Hvordan kan jeg afkorte den førende ciffer af dobbelt værdi i C#,jeg har prøvet Matematik.Runde(doublevalue,2), men det giver ikke kræver resultat. og jeg kunne ikke finde nogen anden metode i Matematik klasse.

For eksempel har jeg værdi 12.123456789 og jeg behøver kun 12.12.

Hvad bør være resultatet, når du giver 12.12890?
Hvad phoenix spørger ønsker du at runde det til 12.13, eller bare afkort det til 12.12… ?
Ja @ærefrygt. Thats højre
jeg vil bare afkorte alle ciffer efter 2.
Derefter Matematik.Runde vil ikke være en mulighed

OriginalForfatteren Firoz | 2009-09-15

12 svar

  1. 27

    EDIT: Det er blevet påpeget, at disse tilgange runde værdien i stedet for afkortning. Det er svært at virkelig afkorte en double værdi, fordi det ikke er virkeligt i den rigtige base… men afkortning af en decimal værdi er mere realistisk.

    Bør du bruge en passende format string, enten brugerdefineret eller standard, fx

    string x = d.ToString("0.00");

    eller

    string x = d.ToString("F2");

    Det er værd at være opmærksom på, at en dobbelt værdi i sig selv ikke “ved” hvor mange decimaler, som det har. Det er kun, når du konvertere det til en streng, at det virkelig giver mening at gøre det. Hjælp Math.Round vil komme i den nærmeste dobbelt værdi til x.xx00000 (hvis du kan se, hvad jeg mener), men det er næsten helt sikkert vil ikke være den nøjagtige værdi x.xx00000 på grund af den måde binær floating point typer arbejde.

    Hvis du har brug for dette for noget andre end string formatering, bør du overveje at bruge decimal i stedet. Hvad betyder den værdi, der reelt repræsenterer?

    Jeg har artikler på binær floating point og decimal floating point i .NETTET, som du måske finder nyttige.

    Tak for dit svar, jeg dont ønsker at konvertere værdien i strengen, så tilbage til dobbelt igen, jeg er nødt til at gemme værdier som. var newVal=Matematik.Runde(oldValue,2) eller nogle af de andre funktioner.
    til strengen og tilbage til dobbelt-ikke vil hjælpe dig alligevel: hvis dobbeltværelse kan ikke repræsentere “12.34” præcis, så du vil for at få ekstra decimaler. Det er enkelt ikke muligt at gemme en dobbeltseng med kun to decimaler.
    Hans er helt rigtigt. Jeg tilføjer et par links i mit svar…
    Wow, af ren chance, dette er den anden accepteret svar af Jon Skeet i den sidste time på her, der har fuldstændig svigtet mig. Dette runder, og OP bedt om at afkorte! Så 3.55555555 bliver 3.56. Og jeg selv op, stemte denne dumme svar, og nu kan jeg ikke tage det tilbage! Dette websted er begyndt at sutte – få folk op, stemte kun på grund af deres eksisterende ry (som “åh det er Jon Skeet, så må det være rigtigt!”).
    Må ikke bekymre dig, i henhold til upvote tæller, er du ikke den eneste, der ikke gør deres hjemmearbejde. 😉

    OriginalForfatteren Jon Skeet

  2. 19

    Hvad har du prøvet? Det virker som forventet for mig:

    double original = 12.123456789;
    
    double truncated = Math.Truncate(original * 100) / 100;
    
    Console.WriteLine(truncated);    //displays 12.12

    OriginalForfatteren LukeH

  3. 3

    Denne kode….

    double x = 12.123456789;
    Console.WriteLine(x);
    x = Math.Round(x, 2);
    Console.WriteLine(x);

    Returnerer denne….

    12.123456789
    12.12

    Hvad er dit ønskede resultat, som er anderledes?

    Hvis du vil beholde den værdi som en dobbelt, og bare stribe af alle cifre efter den anden decimal, og faktisk ikke runde det antal, så kan du blot trække 0.005 fra dit nummer, så denne runde vil derefter arbejde. For eksempel.

    double x = 98.7654321;
    Console.WriteLine(x);
    double y = Math.Round(x - 0.005, 2);
    Console.WriteLine(y);

    Producerer denne…

    98.7654321
    98.76
    hvis x = 12.125 så vil han få 12.13, som ser ud til ikke at være, hvad han ønsker.
    redigeret for at tilføje en runde ned option

    OriginalForfatteren Robin Day

  4. 3
    double original = 12.123456789;  
    
    double truncated = Truncate(original, 2);  
    
    Console.WriteLine(truncated.ToString());
    //or 
    //Console.WriteLine(truncated.ToString("0.00"));
    //or 
    //Console.WriteLine(Truncate(original, 2).ToString("0.00"));
    
    
    public static double Truncate(double value, int precision)
    {
        return Math.Truncate(value * Math.Pow(10, precision)) / Math.Pow(10, precision);
    }
    Det ville være bedre, hvis du forklare den kode, som er godt.
    Din løsning, vil ikke arbejde for 5.02. Hvis du kalder Afkorte(5.02) kan du modtage 5.01, fordi 5.02*100=501.99999999999994

    OriginalForfatteren Carlos Oliveira

  5. 2

    Jeg er sikker på, at der er noget mere .netty derude, men hvorfor ikke bare:-

    double truncVal = Math.Truncate(val * 100) / 100;
    double remainder = val-truncVal;
    “Decimal” type kan tilbyde mindre risiko for, at en floating point afrunding fejl.

    OriginalForfatteren

  6. 2

    Hvordan om:

    double num = 12.12890;
    double truncatedNum = ((int)(num * 100))/100.00;
    Jeg gjorde nogle benchmarking og denne metode er 2x hurtigere end de originale Matematik.Afskær. Tak for at dele
    For at få en lidt mere ydelse erstatte /100 med *0.01 Men det er allerede micro optimering. Jeg gør favorize dette svar.

    OriginalForfatteren JonoW

  7. 2

    Dette kunne arbejde (men ikke testet):

    public double RoundDown(this double value, int digits)
    {
         int factor = Math.Pow(10,digits);
    
         return Math.Truncate(value * factor) / factor;
    }

    Så skal du blot bruge det som denne:

    double rounded = number.RoundDown(2);

    OriginalForfatteren Philippe Leybaert

  8. 0

    objekt antal = 12.123345534;

    streng.Format({“0:00”},antal.ToString());

    OriginalForfatteren JayJay

  9. 0

    Hvis du ønsker at have to point efter decimal uden afrunding nummeret, skal følgende arbejde

    string doubleString = doublevalue.ToString("0.0000"); //To ensure we have a sufficiently lengthed string to avoid index issues
    Console.Writeline(doubleString
                 .Substring(0, (doubleString.IndexOf(".") +1) +2)); 

    Det andet parameter for substring er tæller, og Søg tilbage til nul-baseret indeks, så vi er nødt til at tilføje en til at før vi tilføje 2 decimal værdier.

    Dette svar er forudsat, at den værdi, der IKKE bør være afrundede

    OriginalForfatteren Dan McClain

  10. 0

    For vb.net brug denne udvidelse:

    Imports System.Runtime.CompilerServices
    
    Module DoubleExtensions
    
        <Extension()>
        Public Function Truncate(dValue As Double, digits As Integer)
    
            Dim factor As Integer
            factor = Math.Pow(10, digits)
    
            Return Math.Truncate(dValue * factor) / factor
    
        End Function
    End Module

    OriginalForfatteren George P

  11. 0

    Dette måske for decimal? Jeg skrev min egen coz kæmper for at finde svar på nettet. Denne kode er sandsynligvis ikke fullproof som jeg mangler den erfaring, at fullproof det. I sidste ende vil genopbygge denne metode, til noget simpelt og fantastisk at få arbejdet gjort, at der er færre skridt med samlede robusthed forbedres også. Du kan nemt konvertere det til at tage et input til afstand tæller. men jeg kan ikke garantere at det vil fungere ordentligt med andre end to dec. Ikke som almindeligt input.. Det ser ud til at lide et par 000.000 at arbejde med, da jeg er i behandling med vægt 0000.000 kommer igennem. Også, afrundes priser med dette efter at være blevet beregnet.

    private decimal TruncateToTwoDecimals(string value)
            {
    
                int error_ReturnZeroIfThisIsOne = 0;
                int tempArrayLength = value.Length;
                char[] tempArray = new char[tempArrayLength];
    
                int startCount = 0; //starts the counter when it hits punctuation
                int newCounter = 0; //counts twice to ensure only two decimal places after the comma/period
                int nextArraySize = 1; //gets the size spec ready for the return array/next array (needs to be + 1)
    
                int tempArrayCurrentIndex = 0;
                foreach (Char thisChar in value)
                {
                    tempArray[tempArrayCurrentIndex] = thisChar;
                    tempArrayCurrentIndex++;
                }
    
    
                for (int i = 0; i < tempArrayLength; i++)
                {
    
                    if (tempArray[i].ToString() == "," || tempArray[i].ToString() == ".")
                    {
                        startCount = 1;
                    }
                    if (startCount == 1)
                    {
                        newCounter++;
                    }
    
    
                    if (newCounter > 2)
                    {
                        break;
                    }
                    nextArraySize++;
                }
    
                char[] returnArray = new char[nextArraySize];
                int tempErrorCheckBelow = 0;
                for (int i = 0; i < nextArraySize; i++)
                {
    
    
                    try
                    {
                        returnArray[i] = tempArray[i]; //left array will read [i] till the spot in right array where second decimal and ignore the rest. snip snip
                    }
                    catch (Exception)
                    {
                        if (tempErrorCheckBelow == 2)
                        {
                            MessageBox.Show("OutOfBounds", "Error_ArrayIndex Out Of Bounds @TTTD");
                        }
                        returnArray[i] = Convert.ToChar("0");
                        tempErrorCheckBelow++;
                    }
    
                }
    
                if (tempArrayLength < 1)
                {
    
                    error_ReturnZeroIfThisIsOne++;
    
                    string tempString = "0.0";
                    try
                    {
                        decimal tempDecimal = Decimal.Parse(tempString);
                        return tempDecimal;
                    }
                    catch (Exception)
                    {
    
                        MessageBox.Show("Error_input String received Incorrect Format @TTTD");
                        return 0.00m;
                    }
                }
                else
                {
    
                    error_ReturnZeroIfThisIsOne++;
    
                    string tempString = " ";
                    tempString = new string(returnArray);
                    try
                    {
                        decimal tempDecimal = Decimal.Parse(tempString);
                        return tempDecimal;
                    }
                    catch (Exception)
                    {
                        MessageBox.Show("Error_inputString _0_ @TTTD");
                        return 0m;
    
                    }
                }
    
    
    
            }

    OriginalForfatteren Jono777

  12. 0

    Der er en masse svar ved hjælp af Matematik.Afkort(dobbelt).
    Men den tilgang, ved hjælp af Matematik.Afkort(dobbelt), kan det føre til forkerte resultater.
    For eksempel, vil det vende tilbage 5.01 afkortning 5.02, fordi at multiplicere af dobbelt-værdier ikke kan arbejde præcist og 5.02*100=501.99999999999994

    Afskæring af antallet af cifre af dobbelt værdi i C#

    Hvis du virkelig har brug for denne præcision, overveje, konvertering til Decimal før afkortning.

    public static double Truncate(double value, int precision)
    {
        decimal power = (decimal)Math.Pow(10, precision);
        return (double)(Math.Truncate((decimal)value * power) / power);
    }

    Stadig, at denne tilgang er ~10 gange langsommere.

    OriginalForfatteren PSsam

Skriv et svar

Din e-mailadresse vil ikke blive publiceret. Krævede felter er markeret med *