Page 1 of 1

lambdas in objData (or: the evasive lambda)

Posted: Sat Jan 09, 2010 1:57 am
by alterecco
For a long time we have tried to store functions on objects, for the purpose of saving them across sessions. Up until now this has not been possible, but as a side effect of the new long listing of lambdas, it turns out we can recreate any functions stored on an object. An example

Code: Select all

(block (func1 funcLiteral func1Again)
  (setq func1 (lambda Nil (dbgOutput "test")))
  (objSetData gPlayerShip 'func func1)

  ;; now retrieve it as a literal
  (setq funcLiteral (objGetData gPlayerShip 'func))
  ;; now, to convert it, we do some evalling
  (setq func1Again (eval (eval funcLiteral)))
  (func1Again)
)
Ummm.... woohoooo :D

(func1Again) happily outputs "test" to the console.

Now, func1Again is not the same object as func1, so stuff like closures are not preserved, but otherwise it feels and acts the same.

All in all, good news for dynamic modding :)

Posted: Sat Jan 09, 2010 2:00 am
by Betelgeuse
now we can have different functions on different ships dynamically with the same name 8)

plus it allows us to use local lambda functions at a later date 8)

all in all this is a great discovery

edit: this also allows you to create dynamic events

Posted: Sat Jan 09, 2010 10:06 am
by Betelgeuse
Just did a stress test with a 60k line function and it outputs the correct answer. So we know that code length is not a problem.

warning if you do run this code expect there to be a large pause, the game is not hung it just takes awhile to eval all that code.

Code: Select all

(setq dataStressTest (lambda Nil 
	(block (func1)
		(setq func '(lambda nil (block (a) (setq a 1))))

		(for i 0 60000
			(lnkAppend (item func 2) '(setq a (add 1 a)))
		)

		(objSetData gplayership "stress" func)
		(dbgOutput ((eval (eval (objGetData gplayership "stress")))))


		)
))
minor note I also found that you can make your own lambda functions :twisted: