1

I'm learning Fortran(with the Fortran 2008 standard) and would like to set my integer part precision and decimal part precision for a real variable independently. How do i do this?

For example, let us say that i would like to declare a real variable that has integer part precision as 3 and fractional part precision as 8.

An example number in this above specification would be say 123.12345678 but 1234.1234567 would not satisfy the given requirement.

anuvaramban
  • 151
  • 8
  • For real numbers, Fortran defines only in terms of floating point. In such a model it isn't clear to me what you mean by having independent precision for integer and fractional parts. Can you clarify with an example? [You can, of course, use non-intrinsic things in certain ways.] – francescalus Apr 27 '17 at 12:06
  • Do you mean decimal part and exponential part (instead of integer part)? – SteveES Apr 27 '17 at 12:10
  • @francescalus , i've included an example in the description – anuvaramban Apr 27 '17 at 12:37
  • @SteveES I've added an example, please look at the description now. – anuvaramban Apr 27 '17 at 12:37
  • Why do you want your numbers formatted like that? What are you trying to do with them? Is this for calculations or for output? – SteveES Apr 27 '17 at 12:47
  • @SteveES I am trying to do some calculations for which eight decimal precision is enough but i also want it to be regardless of the number of digits in the integer part. – anuvaramban Apr 27 '17 at 12:52
  • The only real way round it is to define your variables with more precision than you need in the output, so you can be sure your decimal point precision at the end is as much as you require. – SteveES Apr 27 '17 at 13:06

2 Answers2

2

Fortran real numbers are FLOATING point numbers. Floating point numbers do not store the integer part and the decimal part. They store a significand and an exponent.

See how floating point numbers work http://en.wikipedia.org/wiki/Floating-point_arithmetic There is usually one floating point format which your CPU uses and you cannot simply choose a different one.

What you are asking for is more like the FIXED point arithmetic, but modern CPUs and Fortran do not support it natively. https://en.wikipedia.org/wiki/Fixed-point_arithmetic

You can use them in various libraries (even probably Fortran) or languages, but they are not native REAL. They are probably implemented in software, not directly in the CPU and are slower.

  • Thank you for your answer, i have a follow up: so right now i use returned value of selected_real_kind(16) to specify precision using the kind argument, but when i print out the result of the calculations, it seems to be using as if fixed point arithmetic. For instance: since i set selected_real_kind(16), 3.14 ** 3.14 gives 36.3378388801746960712 whereas 10.12 ** 10.12 gives 14873966072.8729692074 where i set the real variable "ar" to 3.14 and 10.12 in consequent runs of the program that simply does ar ** ar – anuvaramban Apr 27 '17 at 12:58
  • 1
    That is a misunderstanding. And be careful, `10.12` is a single (default) precision real constant, unless you declare it with a specific kind. See http://stackoverflow.com/questions/6146005/is-there-a-better-double-precision-assignment-in-fortran-90 – Vladimir F Героям слава Apr 27 '17 at 13:07
  • @anuvaramban Why do you think that is fixed point arithmetic? – SteveES Apr 27 '17 at 13:09
  • @SteveES please see my first comment and the output i got, the total number of digits in both cases is same, this is true if i try for any other numbers. – anuvaramban Apr 27 '17 at 13:32
  • @VladimirF i assign it to a real variable first so i'm effectively doing ar ** ar where the variable ar = 10.12 and has been declared with its kind parameter as directed by the selected_real_kind(16) function's returned value. – anuvaramban Apr 27 '17 at 13:33
  • 3
    No, this is **not true!!!** Please DO read http://stackoverflow.com/questions/6146005/is-there-a-better-double-precision-assignment-in-fortran-90 very carefully. It does not matter what kind `ar` has. 10.12 is SINGLE precision! Also read http://stackoverflow.com/questions/42618704/fortran-handling-large-real-numbers-with-precision?noredirect=1&lq=1 which is simpler. – Vladimir F Героям слава Apr 27 '17 at 13:35
  • 2
    @anuvaramban That is exactly what you would expect in **floating point** arithmetic, which keeps the same number of significant figures (in binary). Fixed point arithmetic loses significant figure precision (with small numbers certainly), but retains decimal point precision. – SteveES Apr 27 '17 at 13:35
  • 2
    @anuvaramban Also, remember that the format of a number on _output_ is **not** the same as its representation _internally_ – SteveES Apr 27 '17 at 13:38
  • @SteveES Thanks! – anuvaramban Apr 27 '17 at 13:53
  • @VladimirF Thanks! – anuvaramban Apr 27 '17 at 13:53
0

I ended up writing a function for this in order to use floating points with the .gt./.lt./.ge./.le./.eq. operators without actually modifying the floating points.

function PreciseInt(arg1, arg2) Result(PreciseInt)
  real*8     arg1       !Input variable to be converted
  integer*4  arg2       !Input # for desired precision to the right of the decimal
  integer*4  PreciseInt !Integer representing the real value with desired precision

  PreciseInt = idnint(arg1 * real(10**arg2))
end function
Adrian W
  • 4,563
  • 11
  • 38
  • 52
Jtox
  • 1