Thread: pointer to structure

  1. #1
    Registered User
    Join Date
    May 2010
    Posts
    50

    pointer to structure

    Hi guys...is it possible to declare in a function a pointer to a "general" structure? I mean
    Code:
    ...
    struct opt_args{
    	double *data;
    	int length_data;
    }; 
    
    static double parabola(double x, struct opt_args *args)
    {
    	int i;
    	double res;
    	for(i=0;i<args->length_data;i++)
    	 {
    		res+= args->data[i]*pow(x,2)-2;
    	 }	
    	return(res);
    }
    is it possible to tell C that in function parabola I want a pointer to a general structure, not neccessarily opt_args? I know that a structure (widely speaking) cannot be used before declaring it, but I am not sure that this implies that my problem is impossible to solve.

  2. #2
    Lurking whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    9,612
    There is actually a language feature for this called variable arguments, but don't get over-excited and just start using it. One of the main reasons C doesn't have things other languages might, like sum(), is because there is *no* type safety.

    And since this is parabolas, can't you just use the quadratic equation to find the roots? I'm assuming that's what you're really doing, anyway ... not good at math

  3. #3
    Registered User
    Join Date
    Sep 2007
    Posts
    1,012
    I'm not sure precisely what you want. Surely you don't want your function accepting any old struct pointer; how would you know what to do with arbitrary ones? I presume you have a fixed set of structs and you'd like to be able to pass any one of them to your function and have it work.

    A variable argument list, as mentioned, would be one way of hacking this to work. You can also use a union filled with structs. Either way, though, C won't be able to automatically figure out types for you; there is no polymorphism built into C.
    Example of union code:
    Code:
    union whatever {
      struct { int type; } base;
      struct { int type; double *p; size_t n; } d;
      struct { int type; int *p; size_t n; } i;
    };
    
    union whatever foo;
    foo.base.type = 1; /* say 1 means double */
    foo.d.p = some_array_of_double;
    foo.d.n = size;
    ...
    switch(foo.base.type)
    {
      case 1: /* pull out the doubles */
        break;
      case 2: /* pull out the ints (or whatever) */
        break;
    }
    So you need to make sure that you keep the pointer, size, and type in sync, and you have to write all the code to pull the proper types out. Pass around a pointer to your union and it's possible, with effort, to have "polymorphism"...

    But I presume the actual solution to your problem (whatever it happens to be) will be simpler than this.

  4. #4
    Registered User
    Join Date
    May 2010
    Posts
    50
    Thanks guys for the aswer. To be precise I explain you my problem. I want to build my own header with some optimization functions. As you probably know an optimization function is "general" and what changes is the function to optimize over.
    Here is some sample code (parabola is only a toy function) where "Bustra_zeroin" is a zero-finder routine.
    Code:
    struct opt_args{
       double *data;
       int length_data;
    };
    
    static double parabola(double x, struct opt_args *args)
    {
       int i;
       double res;
       for(i=0;i<args->length_data;i++)
        {
          res+= args->data[i]*pow(x,2)-2;
        }   
       return(res);
    }
    
    double Bustra_zeroin(         /* An estimate of the root */
        double *ax1,         /* Left border | of the range   */
        double *bx1,         /* Right border| the root is seeked*/
        double *Tol,         /* Acceptable tolerance      */
        int *Maxit,            /* Max # of iterations */
        double (*f)(double, struct opt_args *args),/* Function under investigation   */
        struct opt_args *args      /* Other arguments for f*/
                 )
    
    {
    .....
    .....
        fa = (*f)(a, args); 
        fb = (*f)(b, args);
    .....
    ....
    }
    Hence you see that once you build up your function it must have as a first argument the parameter to optimize over and as a second one a pointer to a structure in order to pass the optional arguments of the function. My concern is to be able to build "Bustra_zeroin" in such a way that the user does not have to edit it to pass his own arguments. The only task that the user must do is to write his own function. As you see, if you use "Bustra_zeroin" you must edit it to specificy the name of the structure pointed.
    Do you understand my problem? Is there, maybe, another smart way to cope with this?
    I apologize for my terrible english!

  5. #5
    Registered User
    Join Date
    May 2010
    Location
    Naypyidaw
    Posts
    1,314
    I'm not clear what you really want to do????
    You can use void pointer as generic pointer.
    Code:
      struct opt_args{
       double *data;
       int length_data;
    };
    
    double Bustra_zeroin(         /* An estimate of the root */
        double *ax1,         /* Left border | of the range   */
        double *bx1,         /* Right border| the root is seeked*/
        double *Tol,         /* Acceptable tolerance      */
        int *Maxit,            /* Max # of iterations */
        double (*f)(double, void *args ),/* Function under investigation   */
        void *args      /* Other arguments for f*/
                 );
    
    static double parabola(double x, void *arg_pointer ) {
          int i;
       double res;
       struct opt_args *args = arg_pointer;  
      /* btw, you forgot to initialize res ??? */
       res = 0.0 ;
       for(i=0;i<args->length_data;i++)
        {
          res+= args->data[i]*pow(x,2)-2;
        }   
       return(res);
    }
    Last edited by Bayint Naung; 06-01-2010 at 03:55 AM. Reason: forget sth

  6. #6
    Registered User
    Join Date
    May 2010
    Posts
    50
    Quote Originally Posted by Bayint Naung View Post
    I'm not clear what you really want to do????
    You can use void pointer as generic pointer.
    Code:
      struct opt_args{
       double *data;
       int length_data;
    };
    
    double Bustra_zeroin(         /* An estimate of the root */
        double *ax1,         /* Left border | of the range   */
        double *bx1,         /* Right border| the root is seeked*/
        double *Tol,         /* Acceptable tolerance      */
        int *Maxit,            /* Max # of iterations */
        double (*f)(double, void *args ),/* Function under investigation   */
        void *args      /* Other arguments for f*/
                 );
    
    static double parabola(double x, void *arg_pointer ) {
          int i;
       double res;
       struct opt_args *args = arg_pointer;  
      /* btw, you forgot to initialize res ??? */
       res = 0.0 ;
       for(i=0;i<args->length_data;i++)
        {
          res+= args->data[i]*pow(x,2)-2;
        }   
       return(res);
    }
    Oh man! It is awesome! now all is working very well! This is what I needed, thanks a lot! Now I am ready to build my header

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Ban pointers or references on classes?
    By Elysia in forum C++ Programming
    Replies: 89
    Last Post: 10-30-2007, 03:20 AM
  2. Direct3D problem
    By cboard_member in forum Game Programming
    Replies: 10
    Last Post: 04-09-2006, 03:36 AM
  3. pointers
    By InvariantLoop in forum C Programming
    Replies: 13
    Last Post: 02-04-2005, 09:32 AM
  4. how to cast a char *mystring to a structure pointer ??
    By hanhao in forum C++ Programming
    Replies: 1
    Last Post: 03-29-2004, 08:59 AM
  5. Pointer to a structure
    By frenchfry164 in forum C Programming
    Replies: 5
    Last Post: 03-16-2002, 06:35 PM