UDF - Sqrt - Math comparison doesn't work

Please check the FAQ (https://www.xyplorer.com/faq.php) before posting a question...
Post Reply
Marco
Posts: 2354
Joined: 27 Jun 2011 15:20

UDF - Sqrt - Math comparison doesn't work

Post by Marco »

Code: Select all

function sqrt($num) {
// Returns the square root of a positive number in base 10.
// Any other argument causes the function to throw an error.
// The result has 10E-13 precision.
// Based on the Babylonian algorithm (see https://en.wikipedia.org/wiki/Methods_of_computing_square_roots#Babylonian_method).
//
//   $num   the positive number in base 10 to calculate the square root of

 assert regexmatches("$num", "[^0-9.,]") == "", "Argument is not a positive number";

 $num = eval($num);
 $eps = eval(1/1000000000000);

 if ($num >= 100) {
  $root = $num/20;
 } elseif ($num >= 2) {
  $root = $num/2;
 } elseif ($num >= 2/100) {
  $root = $num;
 } else {
  $root = $num*10;
 };

 while (abs($root^2 - $num) > $eps) {
  $root = ($root + $num/$root)/2;
 };

 return $root;
}
If you try step-by-step to compute sqrt(5.2) you'll get stuck at a residual of 0.0000000000000195399252334028. And no matter how much I raise $eps, the loop will never terminate. What am I doing wrong?
Tag Backup - SimpleUpdater - XYplorer Messenger - The Unofficial XYplorer Archive - Everything in XYplorer
Don sees all [cit. from viewtopic.php?p=124094#p124094]

bdeshi
Posts: 4256
Joined: 12 Mar 2014 17:27
Location: Asteroid B-612
Contact:

Re: UDF - Sqrt - Math comparison doesn't work

Post by bdeshi »

I'd say it's because XY isn't known for its mathematical excellence. :kidding:

try with this "debug modification"

Code: Select all

 step;
 $acc   = abs($root^2 - $num);
 while ($acc > $eps) {
  $root = ($root + $num/$root)/2;
  $acc =  abs($root^2 - $num);
 };
ed. hint: after a few steps, $acc gets converted to scientific notation, and as long as this is in the form nE-x, XY only takes the -n part for comparison (probably thinking it's salvaging a string)
Icon Names | Onyx | Undocumented Commands | xypcre
[ this user is asleep ]

highend
Posts: 14953
Joined: 06 Feb 2011 00:33
Location: Win Server 2022 @100%

Re: UDF - Sqrt - Math comparison doesn't work

Post by highend »

Just break your loop if you've reached the max convergence.

Code: Select all

 while (abs($root^2 - $num) > $eps) {
      $root = ($root + $num/$root)/2;
      if ($root == $last) { return $root; }
      $last = $root;
 }
One of my scripts helped you out? Please donate via Paypal

Marco
Posts: 2354
Joined: 27 Jun 2011 15:20

Re: UDF - Sqrt - Math comparison doesn't work

Post by Marco »

@Sammy: :o I didn't know XY was capable of E notation - I couldn't even possibly think of that.

@highend: yep, I thought about that solution, but didn't felt elegant to me. But you gave me some inspiration...

Code: Select all

 while ($root != $root_prev) {
  $root_prev = $root;
  $root = ($root + $num/$root)/2;
 };

 return $root;
Tag Backup - SimpleUpdater - XYplorer Messenger - The Unofficial XYplorer Archive - Everything in XYplorer
Don sees all [cit. from viewtopic.php?p=124094#p124094]

Post Reply