calling function in C

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Shiv Ranjan

    calling function in C

    Hi,
    Lets say I have some 10 functions named -

    display1()
    display2()
    display3()
    display4()
    ......
    ......
    display10()

    Assume that all these functions have been defined. Now we have to
    modify the program so that whatever function name is entered by
    keyboard will be invoked. For example if we are accepting string
    display5 from the keyboard then display5() method should be invoked.
    The flow should be generic so that the code need not be modified even
    though some more functions are added.

    If any one has any idea do let me know.

    Regards
    Shiv
  • Richard Heathfield

    #2
    Re: calling function in C

    Shiv Ranjan said:
    Hi,
    Lets say I have some 10 functions named -
    >
    display1()
    display2()
    display3()
    display4()
    .....
    .....
    display10()
    >
    Assume that all these functions have been defined. Now we have to
    modify the program so that whatever function name is entered by
    keyboard will be invoked.
    Construct a lookup table (e.g. hash table, binary search tree, or something
    like that) whose entries are structures containing a key (the name of the
    function, expressed as a string) and a payload (a pointer to the function
    associated with that string). Yes, you will have to recompile whenever you
    add a new entry to the table.

    --
    Richard Heathfield <http://www.cpax.org.uk >
    Email: -http://www. +rjh@
    Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
    "Usenet is a strange place" - dmr 29 July 1999

    Comment

    • Bartc

      #3
      Re: calling function in C

      Richard Heathfield wrote:
      Shiv Ranjan said:
      >
      >Hi,
      >Lets say I have some 10 functions named -
      >>
      >display1()
      >display2()
      >display3()
      >display4()
      >.....
      >.....
      >display10()
      >>
      >Assume that all these functions have been defined. Now we have to
      >modify the program so that whatever function name is entered by
      >keyboard will be invoked.
      >
      Construct a lookup table (e.g. hash table, binary search tree, or
      something like that)
      Any of these will be overkill for this task I think, and likely to give more
      trouble than the main assignment.

      A simple linear search should be fine. Especially as it seems there will be
      one search per keyboard entry.

      --
      Bartc


      Comment

      • Szabolcs Borsanyi

        #4
        Re: calling function in C

        On Wed, May 28, 2008 at 10:20:29AM +0000, Richard Heathfield wrote:
        Shiv Ranjan said:
        >
        Hi,
        Lets say I have some 10 functions named -

        display1()
        [snip]
        display10()

        Assume that all these functions have been defined. Now we have to
        modify the program so that whatever function name is entered by
        keyboard will be invoked.
        >
        Construct a lookup table (e.g. hash table, binary search tree, or something
        like that) whose entries are structures containing a key (the name of the
        function, expressed as a string) and a payload (a pointer to the function
        associated with that string). Yes, you will have to recompile whenever you
        add a new entry to the table.
        >
        --
        Richard Heathfield <http://www.cpax.org.uk >
        (you=OP)
        The nice thing with Richard's solution is that you will not have to recompile
        the part that accesses the lookup table, just the part that builds it.
        Nonetheless, whenever you write a function in C, you'll have to compile it
        sooner or later to get that work. The table itself has to be recomplied too,
        since in standard C you cannot spot a function pointer by the function's name.

        You may want to restrict the portability of your application to
        systems where there is a system-specific way to get a function pointer
        from a string if the funtion is defined in a shared library
        (such as dlsym() on unices.)

        Szabolcs


        Comment

        • pete

          #5
          Re: calling function in C

          Shiv Ranjan wrote:
          Hi,
          Lets say I have some 10 functions named -
          >
          display1()
          display2()
          display3()
          display4()
          .....
          .....
          display10()
          >
          Assume that all these functions have been defined. Now we have to
          modify the program so that whatever function name is entered by
          keyboard will be invoked. For example if we are accepting string
          display5 from the keyboard then display5() method should be invoked.
          The flow should be generic so that the code need not be modified even
          though some more functions are added.
          >
          If any one has any idea do let me know.
          /* BEGIN new.c */

          #include <stdio.h>
          #include <string.h>

          void display1(void);
          void display2(void);
          void display3(void);
          void display4(void);
          void display5(void);

          int main(int argc, char **argv)
          {
          struct {
          char *string;
          void (*func)(void);
          } table[] = {
          {"display1", display1},
          {"display2", display2},
          {"display3", display3},
          {"display4", display4},
          {"display5", display5},
          { NULL, NULL}
          }, *p = table;

          putchar('\n');
          if (argc 1) {
          while (p -string != NULL) {
          if (strcmp(argv[1], p -string) == 0) {
          p -func();
          break;
          }
          ++p;
          }
          if (p -string == NULL) {
          puts("Function not found.");
          }
          } else {
          puts("Not enough argc.");
          }
          return 0;
          }

          void display1(void)
          {
          puts("A");
          }

          void display2(void)
          {
          puts("B");
          }

          void display3(void)
          {
          puts("C");
          }

          void display4(void)
          {
          puts("D");
          }

          void display5(void)
          {
          puts("E");
          }

          /* END new.c */

          --
          pete

          Comment

          • Szabolcs Borsanyi

            #6
            Re: calling function in C

            On Wed, May 28, 2008 at 07:54:53AM -0500, pete wrote:
            Shiv Ranjan wrote:
            >Hi,
            >Lets say I have some 10 functions named -
            >>
            >display1()
            [snip]
            >display10()
            >>
            struct {
            char *string;
            void (*func)(void);
            } table[] = {
            {"display1", display1},
            {"display2", display2},
            {"display3", display3},
            {"display4", display4},
            {"display5", display5},
            { NULL, NULL}
            }, *p = table;
            Surely, you will want to define macros:
            #define F(x) {#x,x}
            #define G(x) F(display ##x)
            {G(1),G(2),G(3) ,{NULL,NULL}}
            rather ther writing everything twice.

            Szabolcs

            Comment

            • Bartc

              #7
              Re: calling function in C


              "Szabolcs Borsanyi" <s.borsanyi@sus sex.ac.ukwrote in message
              news:2008052813 1219.GB13592@kr oto.pact.cpes.s usx.ac.uk...
              On Wed, May 28, 2008 at 07:54:53AM -0500, pete wrote:
              >Shiv Ranjan wrote:
              >>Hi,
              >>Lets say I have some 10 functions named -
              >>>
              >>display1()
              [snip]
              >>display10()
              >>>
              > struct {
              > char *string;
              > void (*func)(void);
              > } table[] = {
              > {"display1", display1},
              > {"display2", display2},
              > {"display3", display3},
              > {"display4", display4},
              > {"display5", display5},
              > { NULL, NULL}
              > }, *p = table;
              Surely, you will want to define macros:
              #define F(x) {#x,x}
              #define G(x) F(display ##x)
              {G(1),G(2),G(3) ,{NULL,NULL}}
              rather ther writing everything twice.
              I think these are just example function names and bodies. The real names
              could be all different. Anyway as this is homework you don't want to appear
              too clever.

              --
              Bartc


              Comment

              • Richard Heathfield

                #8
                Re: calling function in C

                Bartc said:
                Richard Heathfield wrote:
                <snip>
                >Construct a lookup table (e.g. hash table, binary search tree, or
                >something like that)
                >
                Any of these will be overkill for this task I think, and likely to give
                more trouble than the main assignment.
                >
                A simple linear search should be fine.
                A linear search through *what*? Well, gee, a lookup table.

                --
                Richard Heathfield <http://www.cpax.org.uk >
                Email: -http://www. +rjh@
                Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
                "Usenet is a strange place" - dmr 29 July 1999

                Comment

                • Bartc

                  #9
                  Re: calling function in C


                  "Richard Heathfield" <rjh@see.sig.in validwrote in message
                  news:Q4mdnSqGmu FRKqDVnZ2dnUVZ8 uWdnZ2d@bt.com. ..
                  Bartc said:
                  >
                  >Richard Heathfield wrote:
                  >
                  <snip>
                  >
                  >>Construct a lookup table (e.g. hash table, binary search tree, or
                  >>something like that)
                  >>
                  >Any of these will be overkill for this task I think, and likely to give
                  >more trouble than the main assignment.
                  >>
                  >A simple linear search should be fine.
                  >
                  A linear search through *what*? Well, gee, a lookup table.
                  I was referring to your suggestions of using hash tables and binary trees.
                  But, did I really have to clarify that?

                  -- bartc


                  Comment

                  • Richard Heathfield

                    #10
                    Re: calling function in C

                    Bartc said:
                    >
                    "Richard Heathfield" <rjh@see.sig.in validwrote in message
                    news:Q4mdnSqGmu FRKqDVnZ2dnUVZ8 uWdnZ2d@bt.com. ..
                    >Bartc said:
                    >>
                    >>Richard Heathfield wrote:
                    >>
                    ><snip>
                    >>
                    >>>Construct a lookup table (e.g. hash table, binary search tree, or
                    >>>something like that)
                    >>>
                    >>Any of these will be overkill for this task I think, and likely to give
                    >>more trouble than the main assignment.
                    >>>
                    >>A simple linear search should be fine.
                    >>
                    >A linear search through *what*? Well, gee, a lookup table.
                    >
                    I was referring to your suggestions of using hash tables and binary
                    trees.
                    Each of those suggestions is perfectly reasonable, and they offer solutions
                    that are scalable, whereas a linear search is very much an inferior
                    stopgap solution - adequate (barely) if all you want is a pass mark for a
                    college assignment, but not a tool you'd want to use very often for this
                    problem in the Real World. You see, lookup tables have a habit of growing.
                    (See "The Practice of Programming" for a fine example of how adopting a
                    stopgap solution can be costly in the long term.)

                    But, did I really have to clarify that?
                    I am at a loss to understand what you thought you were clarifying.

                    --
                    Richard Heathfield <http://www.cpax.org.uk >
                    Email: -http://www. +rjh@
                    Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
                    "Usenet is a strange place" - dmr 29 July 1999

                    Comment

                    • Bartc

                      #11
                      Re: calling function in C

                      "Richard Heathfield" <rjh@see.sig.in validwrote in message
                      news:YJqdnaKY4-LNR6DVnZ2dnUVZ8 sLinZ2d@bt.com. ..
                      Bartc said:
                      >
                      >>
                      >"Richard Heathfield" <rjh@see.sig.in validwrote in message
                      >news:Q4mdnSqGm uFRKqDVnZ2dnUVZ 8uWdnZ2d@bt.com ...
                      >>Bartc said:
                      >>>
                      >>>Richard Heathfield wrote:
                      >>>
                      >><snip>
                      >>>
                      >>>>Construct a lookup table (e.g. hash table, binary search tree, or
                      >>>>something like that)
                      >>>>
                      >>>Any of these will be overkill for this task I think, and likely to give
                      >>>more trouble than the main assignment.
                      >>>>
                      >>>A simple linear search should be fine.
                      >>>
                      >>A linear search through *what*? Well, gee, a lookup table.
                      >>
                      >I was referring to your suggestions of using hash tables and binary
                      >trees.
                      >
                      Each of those suggestions is perfectly reasonable, and they offer
                      solutions
                      that are scalable, whereas a linear search is very much an inferior
                      stopgap solution - adequate (barely) if all you want is a pass mark for a
                      college assignment, but not a tool you'd want to use very often for this
                      problem in the Real World.
                      I use linear searches all the time. You need a *big* table and/or a *lot* of
                      searches to make those fancy lookups worth the trouble.

                      As described, the OP's problem would need 10 to 100 million function names
                      before a linear search shows a noticeable delay. And at that point I'd
                      suggest a binary search on a pre-sorted table as still being simpler.

                      Possibly there could be extra marks for using a more sophisticated search --
                      provided the OP hasn't been distracted from finishing the main task -- but
                      code which is short, simple, works as intended, and uses an appropriate
                      search method also would have merit.

                      --
                      Bartc


                      Comment

                      • Keith Thompson

                        #12
                        Re: calling function in C

                        "Bartc" <bc@freeuk.comw rites:
                        [...]
                        I use linear searches all the time. You need a *big* table and/or a *lot* of
                        searches to make those fancy lookups worth the trouble.
                        >
                        As described, the OP's problem would need 10 to 100 million function names
                        before a linear search shows a noticeable delay. And at that point I'd
                        suggest a binary search on a pre-sorted table as still being simpler.
                        [...]

                        As described, IIRC, each lookup is done in response to user input.
                        But I wouldn't bet against the program being changed so it needs to do
                        multiple lookups automatically. Once you do that, the difference
                        between, say, half a million comparisons for a linear search vs. 20
                        for a binary search becomes quite significant.

                        --
                        Keith Thompson (The_Other_Keit h) kst-u@mib.org <http://www.ghoti.net/~kst>
                        Nokia
                        "We must do something. This is something. Therefore, we must do this."
                        -- Antony Jay and Jonathan Lynn, "Yes Minister"

                        Comment

                        • Bill Reid

                          #13
                          Re: calling function in C


                          Richard Heathfield <rjh@see.sig.in validwrote in message
                          news:Q4mdnSqGmu FRKqDVnZ2dnUVZ8 uWdnZ2d@bt.com. ..
                          Bartc said:
                          >
                          Richard Heathfield wrote:
                          >
                          <snip>
                          >
                          Construct a lookup table (e.g. hash table, binary search tree, or
                          something like that)
                          Any of these will be overkill for this task I think, and likely to give
                          more trouble than the main assignment.

                          A simple linear search should be fine.
                          >
                          A linear search through *what*? Well, gee, a lookup table.
                          Hey, make it an even simpler direct menu-driven "lookup" as follows:

                          void test_number_1(v oid) { }
                          void test_number_2(v oid) { }
                          void test_number_3(v oid) { }

                          int main(void) {
                          func_menu test_func_menu=
                          {3,3,"Test Menu",
                          {{"Test Number 1",test_number_ 1},
                          {"Test Number 2",test_number_ 2},
                          {"Test Number 3",test_number_ 3}}};

                          puts(program_ti tle);

                          TestFunction :

                          test_func_menu. func_item[run_func_menu(& test_func_menu)].function();

                          if((get_yn_inpu t("\nRun another test?",DEF_NO)) ==YES)
                          goto TestFunction;

                          return 0;
                          }

                          This is how I run "unit tests" on my libraries, as well as
                          other places I need simple quick "function menus"...

                          "func_menu" is of course a struct typedef that contains the
                          number of menu items, the "default" item (you can select it
                          by just pressing RETURN), the menu title, and a list of pairs
                          of menu descriptions and their associated functions.

                          run_func_menu(f unc_menu *func_menu) displays the
                          numbered menu selections to the user, and allows the
                          user to select one, which is the return value (-1) that
                          indexes directly to the function you want to run:

                          test_func_menu. func_item[run_func_menu(& test_func_menu)].function();

                          Actual code omitted for the sake of the OP learning to do stuff
                          like this on his own...

                          ---
                          William Ernest Reid



                          Comment

                          • Chris Thomasson

                            #14
                            Re: calling function in C

                            "Shiv Ranjan" <kumarsr@gmail. comwrote in message
                            news:b7db7a4f-df46-484f-a762-d77dbde380b5@b5 g2000pri.google groups.com...
                            Hi,
                            Lets say I have some 10 functions named -
                            >
                            display1()
                            display2()
                            display3()
                            display4()
                            .....
                            .....
                            display10()
                            >
                            Assume that all these functions have been defined. Now we have to
                            modify the program so that whatever function name is entered by
                            keyboard will be invoked. For example if we are accepting string
                            display5 from the keyboard then display5() method should be invoked.
                            The flow should be generic so that the code need not be modified even
                            though some more functions are added.
                            >
                            If any one has any idea do let me know.
                            You could define a common monotonic sequence number from 1 to N and postfix
                            that on your function names. You extract the sequence number, do a range
                            check, subtract 1 and that's your index. Here is example:
                            _______________ _______________ _______________ _______________ ________
                            #include <stdio.h>
                            #include <stdlib.h>
                            #include <string.h>


                            #define SEQ_MAX_BUFSIZE 3
                            #define SEQ_MAX 5


                            void display_001() { puts("display_0 01"); }
                            void display_002() { puts("display_0 02"); }
                            void display_003() { puts("display_0 03"); }
                            void display_004() { puts("display_0 04"); }
                            void display_005() { puts("display_0 05"); }


                            typedef void (*fp_func_type) (void);


                            static fp_func_type g_func_table[SEQ_MAX] = {
                            display_001,
                            display_002,
                            display_003,
                            display_004,
                            display_005
                            };


                            int main(void) {
                            char func_name[] = "display_00 5";
                            size_t const size = strlen(func_nam e);
                            if (size >= SEQ_MAX_BUFSIZE ) {
                            int const idx = atoi(func_name + size - SEQ_MAX_BUFSIZE );
                            if (idx 0 && idx <= SEQ_MAX) {
                            g_func_table[idx - 1]();
                            } else {
                            fprintf(stderr, "Bad Function Sequence Number!\n");
                            }
                            } else {
                            fprintf(stderr, "Bad Function Name!\n");
                            }
                            return 0;
                            }

                            _______________ _______________ _______________ _______________ ________



                            Just make sure that every function has a different monotonically increasing
                            sequence number, and make sure they the minimum amount is 1, and this scheme
                            can be made to work in certain fairly narrow scenarios...


                            Any thoughts?

                            Comment

                            • Martin

                              #15
                              Re: calling function in C

                              On Thu, 29 May 2008 02:47:51 +0100, Chris Thomasson <cristom@comcas t.net
                              wrote:
                              You could define a common monotonic sequence number from 1 to N and
                              postfix that on your function names. You extract the sequence number, do
                              a range check, subtract 1 and that's your index. Here is example:
                              Running with your idea, I have just a few comments:
                              void display_001() { puts("display_0 01"); }
                              void display_002() { puts("display_0 02"); }
                              void display_003() { puts("display_0 03"); }
                              void display_004() { puts("display_0 04"); }
                              void display_005() { puts("display_0 05"); }
                              I would specify 'void' to specify the functions have no parameters:

                              void display_001(voi d) { puts("display_0 01"); }
                              /* etc */

                              static fp_func_type g_func_table[SEQ_MAX] = {
                              display_001,
                              display_002,
                              display_003,
                              display_004,
                              display_005
                              };
                              I would let the compiler calculate the number of elements:

                              static fp_func_type g_func_table[] = {
                              display_001,
                              display_002,
                              display_003,
                              display_004,
                              display_005
                              };

                              Then, I would calculate the number of elements and store them:

                              #define NELEMENTS(a) (sizeof(a) / sizeof(a[0]))

                              static const size_t func_tab_max = NELEMENTS(g_fun c_table);
                              if (idx 0 && idx <= SEQ_MAX) {
                              The above line then would become:

                              if (idx 0 && idx <= func_tab_max) {

                              --
                              Martin

                              Comment

                              Working...