Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Call a function or method dynamically
Forum Updated to NodeBB v4.3 + New Features

Call a function or method dynamically

Scheduled Pinned Locked Moved General and Desktop
14 Posts 7 Posters 23.7k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • D Offline
    D Offline
    dbzhang800
    wrote on last edited by
    #4

    In fact, you can.

    1. If you have many functions exported in the shared library, you can load the library, and resolve the functions by their name. After that, you get a function pointer.

    2. If you are using Qt, you can call a method function by their name with the help of meta-object.
      @
      QMetaObject::invokeMethod()
      @

    1 Reply Last reply
    0
    • L Offline
      L Offline
      leninbooter
      wrote on last edited by
      #5

      hey, 1+1=2 , I have read about that , but I in the descriptions says
      "Invokes the member (a signal or a slot name) on the object obj."
      so, I thought it can be just used to call a signal or slot, of course, I could declare any of my functions as a slot but I don't know, I thought it wasn't the most convenient. xD I'll try with that

      1 Reply Last reply
      0
      • D Offline
        D Offline
        DeadParrot
        wrote on last edited by
        #6

        If the set of functions you may want to call is known then, yes, you can do this in C++ with what is called a Factory pattern. Very standard stuff.

        1 Reply Last reply
        0
        • U Offline
          U Offline
          utcenter
          wrote on last edited by
          #7

          1+2^^Yes, some vendor specific solutions exist, the C++ standard itself does not support this.

          @Dead - I doubt resolving strings with "if equal" and launching per-determined functions is the intent of the OP.

          EDIT: A clarification:

          In C++, variable, object and function names are irrelevant during runtime, identifies only exist for the convenience of us humans, the compiler converts identifiers to memory addresses and offsets. In this regard, you simply cannot use a string during runtime as an identifier. On the other hand, you can still resolve strings to memory locations of either static or dynamic functions and call them using a function pointer mechanism.

          1 Reply Last reply
          0
          • ZlatomirZ Offline
            ZlatomirZ Offline
            Zlatomir
            wrote on last edited by
            #8

            Using invoke method is the Qt solution, but it works only for slots:
            @
            #include <QMetaobject>
            #include <QObject>
            #include <iostream>

            class MyClass : public QObject
            {
            Q_OBJECT
            public:
            MyClass(QObject *parent) : QObject(parent) {}
            public slots:
            void someMethod() {
            std::cout << "someMethod was called \n";
            }
            };

            int main(int argc, char *argv[])
            {
            MyClass obj(0);
            QMetaObject::invokeMethod(&obj, "someMethod", Qt::DirectConnection);
            return 0;
            }

            #include "main.moc"
            @

            https://forum.qt.io/category/41/romanian

            1 Reply Last reply
            0
            • U Offline
              U Offline
              utcenter
              wrote on last edited by
              #9

              ^^ you can use a similar approach for plain functions, just have to write some boiler plate instead of the MOC, just register the strings and appropriate functions in let's say a map (that's probably how the MOC does it too) and have another function that resolves the string to the appropriate memory address and call it...

              All those approaches still require the code to be designed with that intent to begin with, you have to index all the functions you'd want to call with all the appropriate strings. As for just just calling a function using a string in the same manner identifiers are used in the source code - that is impossible.

              1 Reply Last reply
              0
              • D Offline
                D Offline
                dbzhang800
                wrote on last edited by
                #10

                ;-)

                [quote author="leninbooter" date="1338835994"]hey, 1+1=2 , I have read about that , but I in the descriptions says
                "Invokes the member (a signal or a slot name) on the object obj."
                so, I thought it can be just used to call a signal or slot, of course, I could declare any of my functions as a slot but I don't know, I thought it wasn't the most convenient. xD I'll try with that[/quote]

                It's not required to be signal or slot.

                @
                Q_INVOKABLE

                Apply this macro to definitions of member functions to allow them to be invoked via the meta-object system. The macro is written before the return type, as shown in the following example:
                @

                1 Reply Last reply
                0
                • U Offline
                  U Offline
                  utcenter
                  wrote on last edited by
                  #11

                  A quick example of how you can achieve similar functionality without relying on the meta object API, it is quite simple really:

                  @#include <QMap>
                  #include <QTextStream>
                  #include <QString>

                  QTextStream cout(stdout);
                  typedef void (*foo)(); // define foo to be pointer to void function()
                  QMap<QString, foo> map; // map of strings and foos

                  // a new basic methods
                  void one(){
                  cout << "Function one" << endl;
                  }

                  void two(){
                  cout << "Function two" << endl;
                  }

                  void three(){
                  cout << "Function three" << endl;
                  }

                  //wrapper calling function
                  void callMethod(const QString &name){
                  foo myFoo = map.value(name); //assign new foo to value in the map
                  if (myFoo) myFoo(); //call it if not 0
                  }

                  int main()
                  {
                  //index functions with names
                  map.insert("one", one);
                  map.insert("two", two);
                  map.insert("three", three);

                  //call using strings
                  callMethod("one");
                  callMethod("two");
                  callMethod("three");
                  callMethod("blahblah"); // nothing happens
                  

                  }@

                  1 Reply Last reply
                  0
                  • L Offline
                    L Offline
                    lgeyer
                    wrote on last edited by
                    #12

                    You should use Qt's meta-object implementation unless you have very specific reasons not to do so (for example when your class must not derive from QObject). It is well tested code, works as expected in multi-threaded environments, type-safe and allows for passing arguments and recieving return values.

                    Just derive your class from QObject (if it not already does directly or indirectly) and declare the desired method as slot or Q_INVOKABLE and then use QMetaObject::invokeMethod().

                    1 Reply Last reply
                    0
                    • U Offline
                      U Offline
                      utcenter
                      wrote on last edited by
                      #13

                      Yep, my example was intended to be more of ... an example of how things work, not THE best, safest and most flexible way to do it. My rule of thumb - never just use something, assuming it will magically work, even if going for a complete and more advanced solution have at least basic idea how it works.

                      1 Reply Last reply
                      0
                      • K Offline
                        K Offline
                        KA51O
                        wrote on last edited by
                        #14

                        This made me think about the "Callback approach":http://en.wikipedia.org/wiki/Callback_(computer_programming) . Out of the box it won't work with just strings though.

                        1 Reply Last reply
                        0

                        • Login

                        • Login or register to search.
                        • First post
                          Last post
                        0
                        • Categories
                        • Recent
                        • Tags
                        • Popular
                        • Users
                        • Groups
                        • Search
                        • Get Qt Extensions
                        • Unsolved