[SCRIPT] Floating point math lib v1 upgrade (28-11-06)

The place to discuss scripting and game modifications for X³: Reunion.

Moderators: Moderators for English X Forum, Scripting / Modding Moderators

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

[SCRIPT] Floating point math lib v1 upgrade (28-11-06)

Post by euclid » Wed, 8. Nov 06, 17:02

Some bugs fixed in gcd.xml and cosine.xml (see readme in zip for details) and 3 new main scripts added:

1# sqrt.xml - square root for numbers and fpn arrays with high precision (9 digits).

2# arcsin.xml - inverse sine

#3 arccos.xml - inverse cosine


Remark on inverse trigonometric functions:

In order to provide a moderate time consumption of the algorithm the precision is about 5 digit for input near +/-0.5. However, the precision increases exponenially towards input +/-1 to more than 9 digits.

As usual: any feedback, suggestions, bug reports etc. are welcome :-)

Cheers Euclid

Download link moved up:


New download link
download


You also may want to check this post by dz_duck. He wrote some nice fpn functions which, I'm sure, you will find usefull.

============================================

Version 1.0 uploaded !

Some bugs fixed and 2 main scripts and a subscript added.

As you know there are sine and cosine function available in the SE but they take integer and return integers.

The new floating point main scripts sine.xml and cosine.xml are exactly as the math functions. They are 2pi-periodic over the interval [-1,1]. Also they provider higher precision.

Here an example of placing 21 sats along the sine between 0 and 2pi.
[ external image ]

Any feedback is more than welcome.


====================================

Hotfix uploaded (please overwrite all old files).

Revised and tested all scripts to avoid the array reference problem. As a bonus added a new script 'modulo.xml'. It's like 'mod' but takes also fpn as arguments.

Every feedback is welcome. Please, bug reps. here or via email etc. .

Cheers Euclid
=========


Bug found, see here for details. I'm on it .......

(Update - original post moved down)

Here my first attempt to code a FLOATING POINT MATH LIBRARY VER.0 (16-11-06) for the x3 Script Editor. Feel free to use them in your scripts.

link moved up.E.




Background:
As you may know already the number representation of the SE is restricted. Elementary operations like addition, multiplication and division are difficult to code because the SE can handle only integers within a certain range (for example the greates SE number is 2^(31)-1 = 2147483647) and has also problems with rounding.

Concept:
The SE is reliable within a precision of 9 digits which allow numbers between 0 and 999,999,999 plus, of course, a possible minus sign. So it is possible to represent a floating point number by an array (s,m,e) of size 3, where s is the sign, m is a natural number of max 9 digits and e is the exponent.

Utilities:
The main scripts are add.xml, prod.xml and divide.xml and they do exactly what their names indicate.
Each has 2 parameters as input which can be either integers or the fpn (s,m,e) of a number (see below). The output is an fpn. Note that all these 3 main scripts convert integers to fpn.

In some cases one needs the inverse: integer of an fpn. It is risky because of a possible over or under flow and be cause of truncation errors. The script float2int.xml returns the number 0 for underfow and null for overflow, and in all other cases the integer of the fpn.

Below an example: a simple modification of part of my complexProductionCost script (delete all fpn script calls and uncomment each line to get the original script) to apply the new fpn computation.

Code: Select all

083    if $ware == Energy Cells
084     $price = $complex -> get price of ware Crystals
085 @   $fpn = [THIS] -> call script 'divide' :  integer or floating point array=$price   integer or floating point array=138
086 @   $pcost = [THIS] -> call script 'float2int' :  fpn array (s,m,e)=$fpn
087   *$pcost = $price / 138
088    else
089 @   $prod = [THIS] -> call script 'ware2relval' :  ware=$ware
090     $k = 0
091     $pcost = 0
092     while $k < $nsr
093      $res = $stationresources[$k]
094 @    $ares = [THIS] -> call script 'ware2relval' :  ware=$res
095      $price = $complex -> get price of ware $res
098 @    $fpn = [THIS] -> call script 'prod' :  number 1=$prod  number 2=$price
099 @    = wait 1 ms
100 @    $fpn = [THIS] -> call script 'divide' :  integer or floating point array=$fpn   integer or floating point array=$ares
101 @    = wait 1 ms
102 @    $fpcost = [THIS] -> call script 'float2int' :  fpn array (s,m,e)=$fpn
103      $pcost = $pcost + $fpcost
104   *$dum = $prod * $price
105   *$pcost = $pcost + $dum / $ares
106      $k = $k + 1
107     end
108    end
More info below. Bug reports, suggestions and all feedback welcome.


Cheers Euclid





DEFINITIONS:
----------------

fpn: is an array (s,m,e) of size 3 with s=+/-1 the sign, m natural number and e the exponent.
Example: The number -1/20 = -0.04 = -4E-2 has the fps rep (-1,4,-2)

pnum: is an array(n,e) of size 2 with integer 0<n and exponent 0<e. The corresponding integer n*10^e may not exist (overflow). Hence the notion pnum (pseudo-number).
Example: (12345678,5) = 1234567800000

nstr: is a string of a number
Example: n= 12345000 and nstr='12345000'

revstr: reverse nstr
Example: n= 12345000 has revstr = '00054321'


===================================

MAIN SCRIPTS:
-------------

add
===
Function: sum of two numbers
Input: 2 integer or fpn
Output: fpn
subscripts: int2float, pnum2revstr,addstrings,revstr2pnum, normalize.

prod
====
Function: Product of two numbers
Input: 2 integer or fpn
Output: fpn
Subscripts: int2float, pnum2revstr, prodstrings, revstr2pnum, normalize

divide
======
Function: Divison of first number by second
Input: 2 integer or fpn
Output: fpn
Subscripts: int2float, invert, prod, gcd

float2int
=========
Funtion: maps fpn to integer
Intput: fpn
Output: Integer, NULL if overflow
Subscripts: pnum2revstr, evalpnum, revstr


+++++++++++++++++++++++++++++++++++++


Original post:

I'm wondering if a floating point math library for the SE does already exist, somebody working on it or whether it would be useful at all?

Every feedback is appreciated.

Edit: basic operations have been coded; what else should I include?

Cheers Euclid
Last edited by euclid on Sun, 4. Aug 13, 00:51, edited 12 times in total.

Cycrow
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 22227
Joined: Sun, 14. Nov 04, 23:26
x4

Post by Cycrow » Wed, 8. Nov 06, 17:36

theres no easy way to do floating point calcuations in the engine.

what is your attempting to do ?

what i do usually is multiple it by 1000.

which will give you 3 decimal places, ie, 1234 will = 1.234

then you just divide it at the end to get the final result.

just remember it wont work well for large numbers as they have a maximum of 2billion

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Wed, 8. Nov 06, 19:12

Yes, it's not that easy but if it would be helpful then I'll have a go.

I'm not sure how but was thinking of doing strings rather then numbers because of the limitation to 2^{31} - 1 = 2,147,483,647.

Maybe string rep only for internal use. The rep of the final result could be a number array like (sign,exp,mantissa). Not sure what's the most sensible choice here.


Cheers Euclid

Cycrow
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 22227
Joined: Sun, 14. Nov 04, 23:26
x4

Post by Cycrow » Wed, 8. Nov 06, 19:19

u could take alook at revens math libries, there quite limited however, and they are for X2.

so theres stuff for finding sin, cos, etc which now have commandsi n X3

xeon_1
Posts: 3535
Joined: Thu, 4. Dec 03, 17:16
x4

Post by xeon_1 » Wed, 8. Nov 06, 20:33

ahh don't remind me of flouting point calculations brings back nightmare's form programming siemens plc's

in the end i just multiplyed evernumber with 1000 and did the realy complex stuff my self en feed it in the the darn thing but eveytime they change a parameter i had to recalulate the variabels

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Thu, 9. Nov 06, 20:56

Heheh - yeah it is a pain but multiplying by 1000 doesn't really help if it comes to overflow, i.e. hitting something larger than 2^{31}-1 (btw. a prime number - not really a surprise).

I've decided to go for array rep rather than string because there are just too few string operation.

Each floating point number is now represented by an array of size 3 with entries (s,m,e). Sign = s , mantissa = m and exponent = e. Of course the mantissa is restricted to 9 digits but this provides a relative error of about 10^{-6} which is not too bad IMHO.


Already started coding :grin:

Int2float, float2int, normalize, overflowm and prod are done which allows multiplication.

I have a little problem with the overflow handling of division but hope to sort that out soon.


Cheers Euclid

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Sat, 11. Nov 06, 22:22

I've done the elementary operations addition, subtraction, multiplication and division.

The SE already provides fairly good functions for sine, cosine and sqrt. So I won't do them in floating point unless someone needs it.



What else would be of interest?


Cheers Euclid

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Fri, 17. Nov 06, 03:02

*bump*

Initial post updated. Version 0 ready for download.

Please report any bug - all feedback welcome.


Cheers Euclid

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Sat, 18. Nov 06, 23:01

Hotfix uploaded (see first post).

Cheers Euclid

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Sun, 26. Nov 06, 18:33

New version uploaded.

Cheers Euclid

voxol
Posts: 429
Joined: Sun, 30. Oct 05, 14:42
x3

Post by voxol » Mon, 27. Nov 06, 03:35

An inverse sin/cos would be handy as well. Its easy to get a direction vector from one location to another, but then not so easy to calculate the orientation of that vector in reference to e.g. the orientation of a ship. It would be very useful to have a script command to order a ship to rotate about its axis to point at a target, for example. One idea would be standalone turret 'ships'... in fact my mind is brimming with ideas for such a script...

If you could include such a function, or even just the inv cos/sin, then that would be awesome. I've played with the SEs trig functions for hours on end and never got anything useful, though my maths is rusty to say the least.

Keep up the good work!

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Tue, 28. Nov 06, 02:32

Thanks for the feedback, voxol :-)

The download now contains 3 new main scripts: sqrt.xml and the 2 inverse trigonometric functions arcsine.xml and arccosine.xml.

Note that the precision is not that good for radiants near +/- 0.5 (about 5 digits). If your application requires higher precision please let me know and I'll look into it.

Also fixed some bugs in gcd.xml and in cosine.xml.


Cheers Euclid

User avatar
dz_duck
Posts: 77
Joined: Tue, 15. May 07, 17:28
x3

Post by dz_duck » Sun, 2. Sep 07, 07:35

euclid, I've created some more floating point functions, and I thought you might like to add them to this library. The scripts can be found here.

The scripts are:
abs: absolute value
arctangent: one-input arctan
arctangent2: two-input arctan
ensurefpn: converts a number or fpn to a fpn (replaces the initial block of code that's in a lot of the scripts)
eq: ==
ge: >=
gt: >
le: <=
lt: <

I've tested all of these to the best of my ability, but I don't guarantee that they won't misbehave if given funny inputs.

Also, have you considered changing the script names to something like lib.float.add, etc., to keep things more organized? It looks possible to change the text in the xml file directly, which would be pretty easy with a search and replace. I could give it a shot if you're interested. Maybe make the library into a .spk too...?

================================

EDIT/WARNING: The script aaa.xml may cause X3 to CTD when enabling the script editor. It's just a testing script, so it's not necessary for anything, and can be safely removed.
Last edited by dz_duck on Fri, 5. Oct 07, 04:50, edited 1 time in total.

Ayreus
Posts: 82
Joined: Fri, 27. Jul 07, 00:10
x3

Post by Ayreus » Sun, 2. Sep 07, 09:13

Just wondering (I know this is an old topic), are you planning on adding more advanced functions like series summations and products that would build on your floating point library? For instance, the kind of products I'm thinking of are this:

[ external image ]

Anyway, I've been wanting to put together a statistics library for awhile now but just haven't had time to get down to doing it. Kudos for the math library, you've answered my prayers on that account!

User avatar
euclid
Moderator (Script&Mod)
Moderator (Script&Mod)
Posts: 13293
Joined: Sun, 15. Feb 04, 20:12
x4

Post by euclid » Tue, 4. Sep 07, 12:06

dz_duck:

Thanks for the great job. For the moment I suggest to keep yours separated for any user could just download both if needed.

Resone is that some of my fundamental scripts are not yet optimized and I'm not sure when or if I ever get to do that.


Ayreus:

That's an interesting thought. I've started some basic statistical functions but soon lost interest.

The main reason is that executing scripts of this complexity soon becomes inefficient with regards to their execution times (they just take too long).

For example I've wrote a script that (approximately) distributes n points uniformely on the unit sphere. But already for more than 20 points the code took about 3 min. !!

However feel free to write more fpn functions and post them here.


Cheers Euclid

Ayreus
Posts: 82
Joined: Fri, 27. Jul 07, 00:10
x3

Post by Ayreus » Tue, 11. Sep 07, 01:24

Took your advice; I've written a math library that also provides a framework that allows you to chain multiple functions together to create mathematical formulae. So far I've got an integer factorial, series summation and series product function that have been completely debugged. I'm also working on an integral function that uses simple Riemann sums (using the summation function), though being limited to integer values makes it somewhat arbitrary at the moment. The beauty of the thing, though, is that you can write your own equation scripts and add references to them in the main function table script for the stock functions to use. Overhead will undoubtedly become an issue, but I think I've managed to mitigate it to a large extent by capitalizing on recursive script calls...Requires more memory in the stack but (hypothetically) cuts down on processing time, and allows the script engine to even-out execution with the global pool of concurrent processes.

As an example, I was able to run the summation function 30 iterations through a dependent equation script without taking any noticeable performance hits. The summation I used was:

E (a*n + b!) : n = 1...30, a = 10, b = 5

a and b were passed as function parameters, so multivariate computations are possible. I had chained the integer factorial function as a dependent of the equation script to create b!, so this was strictly a sub-optimal definition which still managed to perform well.

I plan to run more extensive trials once I have the integral function debugged. Curiously, subdividing a domain range based on a precision index seems to be creating some issues, despite the fact the I've made sure that division results in integer values for the abscissa during my trials. I've even had X3 crash on me a couple of times when I went to the logbook to check the output. Fortunately none of the other functions suffer from this problem. Not entirely sure why that should be happening...I can only guess at the SE's internal division function. The integral function is the only function that uses it, and I already know that the summation function works perfectly fine, which makes the division op the likely suspect. I wonder, have you noticed any similar problems with the script editor's division function?

Anyway, I still need to do more code clean-up and optimization after I solve the integral function problem, but once finished I'll post the download location on this thread (with your permission). It'll have to wait a bit until I've finished some other work, though.

User avatar
dz_duck
Posts: 77
Joined: Tue, 15. May 07, 17:28
x3

Post by dz_duck » Tue, 11. Sep 07, 19:05

Would you mind me asking why you'd want to do integrals and series in X3? It seems interesting to me. If the calculations are not time-sensitive, you may want to do them externally, using Cycrow's GUI stuff maybe. I think this would help computers with multiple CPU cores.

Ayreus
Posts: 82
Joined: Fri, 27. Jul 07, 00:10
x3

Post by Ayreus » Tue, 11. Sep 07, 23:18

dz_duck wrote:Would you mind me asking why you'd want to do integrals and series in X3?
Not at all. Series and integrals are needed for some statistical functions to work. For instance, z-scores (or points on the normal curve) are computed using integrals; lookup tables containing z-scores are too vast to efficiently store in a resource file given their xml format without a whole lot of string parsing and/or looping, which would likely require at least as much processing time and waste precious resource file space since there are only so many resource file designations to go around.

Series and integral functions are also occasionally needed to implement rational agents (Artificial Intelligence), especially those that use expected utility functions and probabilistic reasoning in general, as well as constraint-based reasoning. The only problem with trying to write these kinds of agents is probably going to be the processing limitations imposed by the X3 SE; I have yet to run into any definite upper limits on what it can handle, but it would be completely valid to point out that there's a good chance the processing overhead is going to kill the effort before it gets very far.

Personally, I would agree that Cycrow's custom GUI would be a much better place for this, but at the moment that's not possible. I suppose you could consider this a practice run.

My apologies to Euclid; I don't mean to monopolize your thread. If there's enough interest in this then I'll post a separate one. Since I was planning to eventually incorporate your floating point library, I'll make sure that you get the credit you deserve for your work. :)

Jakesnake5
Posts: 2880
Joined: Fri, 17. Feb 06, 04:55
x4

Post by Jakesnake5 » Wed, 9. Jan 08, 23:49

@Euclid

I just recently took a look at, and tried out you're functions. VERY usefull.

I applied them to a construction bit for the Exodus Mod.

My original 'fix' for calculating the necessary value from the ships RelVal is, well, imprecise, but close without slamming into the overflow limit. Eladan used it in his Scrap Ships at HQ/TL scripts (the first in the bonus pack).

Using your FP scripts significantly increased the accuracy.

Going to go poke Eladan about it. :)
Perfection is in the hands of God, we bags of dirt can only do the best we can©
[ external image ]
Modders are a source of ideas to help the Game Makers improve what they have made. Cherrish them, for they are the fruit of thy labors.©

eladan
Posts: 7168
Joined: Sat, 7. Jan 06, 16:01
x4

Post by eladan » Thu, 10. Jan 08, 01:19

@Jakesnake - consider me informed! (You didn't take any chances I'd miss it! :D)

Post Reply

Return to “X³: Reunion - Scripts and Modding”