28

I need to be able to use the standard math functions on decimal numbers. Accuracy is very important. double is not an acceptable substitution. How can math operations be implemented with decimal numbers in C#?

edit I am using the System.Decimal. My issue is that System.Math does not work with System.Decimal. For example, the following functions do not work with System.Decimal:

  • System.Math.Pow
  • System.Math.Log
  • System.Math.Sqrt
Peter O.
  • 32,158
  • 14
  • 82
  • 96
LunchMarble
  • 5,079
  • 9
  • 64
  • 94

3 Answers3

19

Well, Double uses floating point math which isn't what you're after unless you're doing trigonometry for 3D graphics or something.

If you need to do simple math operations like division, you should use System.Decimal.

From MSDN: The decimal keyword denotes a 128-bit data type. Compared to floating-point types, the decimal type has a greater precision and a smaller range, which makes it suitable for financial and monetary calculations.

Update: After some discussion, the problem is that you want to work with Decimals, but System.Math only takes Doubles for several key pieces of functionality. Sadly, you are working with high precision numbers, and since Decimal is 128 bit and Double is only 64, the conversion results in a loss of precision.

Apparently there are some possible plans to make most of System.Math handle Decimal, but we aren't there yet.

I googled around a bit for math libraries and compiled this list:

  1. Mathdotnet, A mathematical open source (MIT/X11, LGPL & GPL) library written in C#/.Net, aiming to provide a self contained clean framework for symbolic algebraic and numerical / scientific computations.

  2. Extreme Optimization Mathematics Library for .NET (paid)

  3. DecimalMath A relative newcomer, this one advertises itself as: Portable math support for Decimal that Microsoft forgot and more. Sounds promising.

Brian MacKay
  • 31,133
  • 17
  • 86
  • 125
  • I am trying to use System.Decimal, but it does not work with System.Math – LunchMarble May 04 '11 at 18:51
  • 1
    Well for arithmatic, use Decimal, and when you need to do System.Math.Log, cast it to Double and then back again. – Brian MacKay May 04 '11 at 18:53
  • I need accuracy, the cast forces a loss of accuracy. – LunchMarble May 04 '11 at 18:54
  • Ah, you mean the cast to Double forces a loss of precision. Check out this answer: http://stackoverflow.com/questions/803225/when-should-i-use-double-instead-of-decimal/803260#803260 – Brian MacKay May 04 '11 at 18:59
  • 1
    @Storm Kiernan: You definitely need a third party library. Apparently this is supposed to make its way into the framework eventually, but it isn't in yet. I'm googling around for it now. There are some C libraries and maybe there's a C# wrapper for one. – Brian MacKay May 04 '11 at 19:07
  • @Brian MacKay: Alright, sounds good. Thank you for your help! – LunchMarble May 04 '11 at 19:09
  • Sadly the answer you link to in the question appears to have been deleted. – Jeff B Apr 14 '17 at 13:43
  • 1
    @JeffBridgman Not sure what the protocol is here, but to solve this, I brought in the relevant content from the answer in that deleted question, and did my best to give proper credit. Thanks for the heads up. – Brian MacKay Apr 17 '17 at 02:21
  • Note: The Extreme Optimization library is no longer a free product. Likewise, the IMSL C# link is no longer valid and redirects to a generic features page at IMSL. I could not find a C# source library there. – RBarryYoung Nov 19 '20 at 17:39
  • 1
    @RBarryYoung Thanks - confirmed and updated. I also checked out the one Ramin mentioned below, it looks like it might be worth a look. – Brian MacKay Nov 20 '20 at 22:01
14

DecimalMath contains all functions in System.Math class with decimal argument analogy

Note : it is my library and also contains some examples in it

Ramin Rahimzada
  • 452
  • 6
  • 10
  • 2
    If you're going to promote your own library, please give [disclosure](https://meta.stackexchange.com/questions/229085/how-to-offer-personal-open-source-libraries/229091#229091) that you wrote it. I'm assuming that you did because the GitHub username matches your SO username. It would also be helpful to give examples of how you would accomplish what the OP wanted rather than just linking to your library. – bcsb1001 Dec 23 '17 at 22:25
  • Yes,Its my library and i develop it for my needs and shared commonly,I rewrite Math library using Taylor series of each function and some other tricks, I mean all examples are the same as Math class so no need extra example, but İt may be my ignorance of not disclosing that it is mine – Ramin Rahimzada Dec 24 '17 at 00:02
  • I really like this one. – FranzHuber23 Jun 07 '19 at 07:12
8

You haven't given us nearly enough information to answer the question.

decimal and double are both inaccurate. The representation error of decimals is zero when the quantity being represented is exactly equal to a fraction of the form (x/10n) for suitable choices of x and n. The representation error of doubles is zero when the quantity is exactly equal to a fraction of the form (x/2n) again for suitable choices of x and n.

If the quantities you are dealing with are not fractions of that form then you will get some representation error, period. In particular, you mention taking square roots. Many square roots are irrational numbers; they have no fractional form, so any representation format that uses fractions is going to give small errors.

Can you explain what you are doing in hugely more detail?

Eric Lippert
  • 647,829
  • 179
  • 1,238
  • 2,067
  • 5
    -1 I thought the question provided enough information. He's using decimals and he wants to use the built-in .NET class operations in his calculations, but they only take doubles. – contactmatt Jan 21 '15 at 20:27