Calling a function from a string?

BlitzMax Forums/BlitzMax Programming/Calling a function from a string?

Retimer(Posted 2008) [#1]
How can I call a function passed by a variable?

Ex:

function Function_Test(Val:int)
    print val
end function

callfunction("function_test(5)")


What would the code be within the 'callfunction' command? assuming this is possible..

Thanks


Gabriel(Posted 2008) [#2]
I don't think you can. The functions won't have those names when they're compiled so it wouldn't know what to call. You either want a function pointer or a script engine. If you had a function written in Lua, you could call that by name.


plash(Posted 2008) [#3]
As far as I know you can't simply use reflection to get all global functions, only ones that exist in a type (or maybe not even that, just methods).

This should work:
SuperStrict

Framework brl.reflection
Import brl.standardio

Type TFuncContext
	
	Method CallMe:String(num:Int, str:String)
		
		Print num + " " + str
		
	   Return "You just Called me.."
	   
	End Method
	
End Type

Global CallContext:TFuncContext = New(TFuncContext), CallContext_ID:TTypeId = TTypeId.ForObject(CallContext)

Local args:Object[] =["52", "Hello!"]
Print "Returned from function: " + String(CallFunction("callme", args))

Function CallFunction:Object(name:String, args:Object[]) 
  Local meth:TMethod = CallContext_ID.FindMethod(name)
	
	Return meth.Invoke(CallContext, args)
	
End Function


And checking for incorrect argument types is very simple, take a look at TMethod.ArgTypes:TTypeId[]()

EDIT: Confirmed, you can't get function ids through reflection (makes sense), only methods.


Retimer(Posted 2008) [#4]
If you had a function written in Lua, you could call that by name.

Lua is exactly what i'm trying to challenge, speed-wise and simplicity for my engine.


@plash
Perfect example, thanks a lot...that should work. I haven't touched reflection until now.


Otus(Posted 2008) [#5]
Be warned that reflection only allows access to Fields and Methods. AFAIK there's no way to call a function.


grable(Posted 2008) [#6]
Lua is exactly what i'm trying to challenge, speed-wise and simplicity for my engine.

Youd be hard pressed to do better than Lua, its one of the fastest AND simplest scripting engines out there.

But i can understand the "roll your own" aproach, i like to do that as well ;)


TomToad(Posted 2008) [#7]
I guess you could use a Tmap to hold the function names and pointer. Don't know if it would actually be faster



CS_TBL(Posted 2008) [#8]
Events
--------

event.id=SomeEventname ' meaning you are calling one of your functions
event.extra="Kickmybutt" ' "name" of the function
emitevent event

And further on you have a number of event-hooked functions, each function listens to the SomeEventname id, but only one listens to event.extra "Kickmybutt".

Optionally you could do:

event.source=Self

just before emiting the event and you can then send along all the variables you want (the event-hooked function has pre-defined args).


Retimer(Posted 2008) [#9]
Thanks TomToad, i'll compare that as well.



Youd be hard pressed to do better than Lua, its one of the fastest AND simplest scripting engines out there.



For certain uses..

I'm going for a bit more newb friendly syntax, and unlike lua, i'm not including function creation within the scripting. All functions will be part of my core engine, so there's less under the hood allowing things to speed up. I'm also working on a compiler for my scripts to load them into memory MUCH faster (binary).

So far, just splitting strings and reading the values to a string array, then finding the corresponding functions based on the string finds itself about 20% faster alone. If compiling the scripts via bank, and loading them into an integer array, i'm sure i'll get a lot more speedup then that.


Lua is great at handling everything properly, but I don't need all of its functionality, nor does my scripting need such expansion.


grable(Posted 2008) [#10]
I wasnt trying to keep you from making your own, far from it.
Compilers, Virtual Machines and the like is my favorite subject :D

If compiling the scripts via bank, and loading them into an integer array, i'm sure i'll get a lot more speedup then that.

With a simple Stack Machine you can get very far with quite good performance.

But you could just as well use an AST interpreter if your language doesnt require any math and such...

Myself am working on a LISP interpreter that will compile down to a VM (one i made in assembler), and possibly to x86 as well (gotta have goals right? ;)
This is what i love about BlitzMax, being able to intermix ASM,C,etc with bmx as glue.

Anyways, keep it up!


Blueapples(Posted 2008) [#11]
Take a look at the MicroC module, it does stuff like this. There's BASIC syntax parser for it now too.


plash(Posted 2008) [#12]
This is what i love about BlitzMax, being able to intermix ASM,C,etc with bmx as glue.
You can Import assembly code? (!)


Otus(Posted 2008) [#13]
You can Import assembly code? (!)


That's one of the few neat things that are actually documented.

Language->Advanced topics->Interfacing with C:
The currently supported non-BlitzMax source file types are: .c (C); .cpp (C++); .cxx (C++); .m (ObjectiveC); and .s (Assembler).



JoshK(Posted 2008) [#14]
That is a neat idea. Something like this:

FunctionPointer:Byte( funcname$ )