Author Topic: Rounding Real Numbers  (Read 7092 times)

0 Members and 2 Guests are viewing this topic.

MeasureUp

• Bull Frog
• Posts: 441
Rounding Real Numbers
« on: April 29, 2013, 12:56:16 AM »
The "fix" function converts a real number to the nearest smaller number.
How to round a real number to the nearest larger number?

Kerry

• Mesozoic relic
• Seagull
• Posts: 11654
• class keyThumper<T>:ILazy<T>
Re: Rounding Real Numbers
« Reply #1 on: April 29, 2013, 01:14:54 AM »
Perfection is not optional.
Everything will work just as you expect it to, unless your expectations are incorrect.
Discipline: None at all.

--> Donate to theSwamp<--

MeasureUp

• Bull Frog
• Posts: 441
Re: Rounding Real Numbers
« Reply #2 on: April 29, 2013, 02:03:16 AM »
Thanks Kerry.

Marc'Antonio Alessi

• Swamp Rat
• Posts: 1199
• Marco
Re: Rounding Real Numbers
« Reply #3 on: April 29, 2013, 05:54:45 AM »
The "fix" function converts a real number to the nearest smaller number.
How to round a real number to the nearest larger number?
Code: [Select]
`; Rounding function - Doug Broad - 02/19/2003; Additional credits: Joe Burke, Peter Toby; Original name: (defun Round (value to) ...);; Examples:; (ALE_Number_Round 1.11111          1) => 1; (ALE_Number_Round 1.11111        0.1) => 1.1; (ALE_Number_Round 1.11111       0.01) => 1.11; (ALE_Number_Round 1.11111      0.001) => 1.111; (ALE_Number_Round 1.11111     0.0001) => 1.1111; (ALE_Number_Round 1.11111  0.0000001) => 1.11111;; (ALE_Number_Round 1.565656        10) => 0; (ALE_Number_Round 1.565656         1) => 2; (ALE_Number_Round 1.565656       0.1) => 1.6; (ALE_Number_Round 1.565656      0.01) => 1.57; (ALE_Number_Round 1.565656     0.001) => 1.566; (ALE_Number_Round 1.565656    0.0001) => 1.5657; (ALE_Number_Round 1.565656   0.00001) => 1.56566; (ALE_Number_Round 1.565656 0.0000001) => 1.56566;(defun ALE_Number_Round (ImpVal To_Val)  (setq To_Val (abs To_Val))  (*    To_Val    (fix      (/        (          (if (minusp ImpVal)            -            +          )          ImpVal          (* To_Val 0.5)        )        To_Val      )    )  ))`

roy_043

• Water Moccasin
• Posts: 1876
Re: Rounding Real Numbers
« Reply #4 on: April 29, 2013, 08:22:38 AM »
@Marc'Antonio Alessi
To be exact:
Your function rounds to infinity and not to the nearest largest number.
(ALE_NUMBER_ROUND -1.5 1) => -2

Lee Mac

• Seagull
• Posts: 12502
• London, England
Re: Rounding Real Numbers
« Reply #5 on: April 29, 2013, 08:28:35 AM »
Here are my functions for rounding up & down:

Code - Auto/Visual Lisp: [Select]
1. ;; Round Up  -  Lee Mac
2. ;; Rounds 'n' up to the nearest 'm'
3.
4. (defun LM:roundup ( n m )
5.     (cond
6.         ((equal 0.0 (rem n m) 1e-8) n)
7.         ((< n 0) (- n (rem n m)))
8.         ((+ n (- m (rem n m))))
9.     )
10. )
11.
12. ;; Round Down  -  Lee Mac
13. ;; Rounds 'n' down to the nearest 'm'
14.
15. (defun LM:rounddown ( n m )
16.     (cond
17.         ((equal 0.0 (rem n m) 1e-8) n)
18.         ((< n 0) (- n (rem n m) m))
19.         ((- n (rem n m)))
20.     )
21. )

Code - Auto/Visual Lisp: [Select]
1. _\$ (LM:roundup 3.2 2)
2. 4.0
3. _\$ (LM:rounddown 3.2 2)
4. 2.0

MeasureUp

• Bull Frog
• Posts: 441
Re: Rounding Real Numbers
« Reply #6 on: April 29, 2013, 07:29:42 PM »
Thanks to everyone's tips.
Cheers!

Marc'Antonio Alessi

• Swamp Rat
• Posts: 1199
• Marco
Re: Rounding Real Numbers
« Reply #7 on: April 30, 2013, 04:23:05 AM »
@Marc'Antonio Alessi
To be exact:
Your function rounds to infinity and not to the nearest largest number.
(ALE_NUMBER_ROUND -1.5 1) => -2
Thanks for pointing that.
:kewl:

CAB

• Global Moderator
• Seagull
• Posts: 10395
Re: Rounding Real Numbers
« Reply #8 on: May 05, 2013, 09:03:56 PM »
I've reached the age where the happy hour is a nap. (°¿°)
Windows 10 core i7 4790k 4Ghz 32GB GTX 970

irneb

• Water Moccasin
• Posts: 1794
• ACad R9-2016, Revit Arch 6-2016
Re: Rounding Real Numbers
« Reply #9 on: May 07, 2013, 08:08:41 AM »
An optimized version I've taken from here: http://blog.frama-c.com/index.php?post/2013/05/02/nearbyintf1

Seeing as AutoLisp reals are always doubles, you could use the add (0.5 - one double increment less = 0.49999999999999994) idea.
Code - Auto/Visual Lisp: [Select]
1. (defun round (val)
2.   (fix (+ val 0.49999999999999994)))
Common sense - the curse in disguise. Because if you have it, you have to live with those that don't.

bruno_vdh

• Guest
Re: Rounding Real Numbers
« Reply #10 on: May 07, 2013, 08:28:16 AM »
Hello,

Good idea, but be careful with the type of the return value.
Code: [Select]
`\$ (type (round 2.49))INT`
I think this is preferable
Code: [Select]
`\$ (defun round (val)  (float (fix (+ val 0.49999999999999994))))ROUND_\$ (type (round 2.49))REAL`

irneb

• Water Moccasin
• Posts: 1794
• ACad R9-2016, Revit Arch 6-2016
Re: Rounding Real Numbers
« Reply #11 on: May 08, 2013, 01:38:37 AM »
It depends on what you want. If you always do want a real, then add the float conversion as per your code. However, Lisp usually does not care between int & real, performing mathimatical calcs would convert to whatever is needed automatically. E.g. see the return on a very large real value from my code - if it's larger than the signed 32bit int max/min then the return stays a real.
Code: [Select]
`_\$ (round 1234567890)1234567890_\$ (round 12345678901)1.23457e+010`
There are some functions which do care about the type though (the rtos and itoa e.g.). IMO this is an inconsistency - I'd have much more use for a num-to-str function, but I get why the 2 are there (ability to format decimals/fractions for reals but not ints). One of the reasons for the format function in this thread: http://www.theswamp.org/index.php?topic=39158.45
Common sense - the curse in disguise. Because if you have it, you have to live with those that don't.

chlh_jd

• Guest
Re: Rounding Real Numbers
« Reply #12 on: May 10, 2013, 04:43:28 AM »
Code: [Select]
`(defun round (num pre / b)  ;; Enhanced rounding  ;; num -- a number  ;; pre -- precision , type in an interg like -1 0 2 ...  ;; (round 1.23456789 3) --> 1.235  ;; (round 1.23456789 0) --> 1.0  ;; (round 123456789 -3) --> 1.23457e+008  ;; (round -98764567 -5) --> -9.88e+007  (setq b (expt 10.0 pre))  (/ (fix (+ (* num b) (* 0.5 (sign num)))) b)    )(defun sign (x) (cond ((minusp x)-1.)(1.0)))`

VovKa

• Swamp Rat
• Posts: 1352
• Ukraine
Re: Rounding Real Numbers
« Reply #13 on: May 11, 2013, 04:14:20 AM »
in case anyone would need another rounding rule
http://www.theswamp.org/index.php?topic=23142.msg278394#msg278394