I have an array of function pointers int (*oper_ptr[4])(int, int) = {add, sub, mul, divi}; for the below functions which simply perform a standard operation on two passed integers:
int add(int num_a, int num_b);
int sub(int num_a, int num_b);
int mul(int num_a, int num_b);
int divi(int num_a, int num_b);
What is the best way to pass this array into another function. I have tried:
void polish(char* filename, int (*oper_ptr[4])(int, int)) with for e.g., oper_ptr[0](num_a, num_b); to call the first function.
The way you have done it works. But as always with function pointers, it's a bad idea to use them without typedef:
typedef int operation (int num_a, int num_b);
void polish (char* filename, operation* op[4]);
Related
What exactly does putting an * in front of function name mean?
Also how are these two codes different from one another?
int *modify_array(int *array, int size);
int (*modify_array)(int *array, int size);
int *modify_array(int *array, int size);
int (*modify_array)(int *array, int size);
First one: modify_array is a function that accepts two arguments and returns a pointer to an int.
Second one: modify array is a pointer to a function that accepts two arguments and returns an int.
Example, names changed
#include <stdio.h>
int *fx(int *, int); // function prototype
int (*fp)(int *, int); // variable declaration
int *fx(int *a, int n) { // function definition
return a+n; // address of a[n]
}
int fx2(int *a, int n) { // function definition, prototype, and declaration
return a[n];
}
int main(void) {
int ar[] = { 0, 42, 0, 0 };
fp = fx2; // make the pointer point to a function of the right kind
printf("%p %d\n", fx(ar, 1), fp(ar, 1));
return 0;
}
Note about calling a function through the pointer fp: you can dereference the pointer or use the pointer directly
#include <math.h>
double (*fx)(double) = sin;
sin(3.1416/4) == (*fx)(3.1416/4) == fx(3.1416/4);
// declares a function which returns an int (usually 4 bytes)
int modify_array_1(int *array, int size);
// declares a function which returns an pointer (usually 8 bytes)
// that pointer is the memory address of a 4-byte int
int *modify_array_2(int *array, int size);
// declares a variable of type pointer (usually 8 bytes) which points to a function
// the function has the signature int SOMETHING(int *array, int size)
int (*modify_array_3)(int *array, int size);
// now, because modify_array_1 has that signature, you can run this:
modify_array_3 = modify_array_1;
In the first line, modify_array is a function that returns a pointer to int;
But your second line is a pointer to function, so modify_array is a pointer to functions that return an int and accept two parameters, array and size.
I looked but couldn't find a direct reference for this question. I'm new to function pointers (and C), so I don't know all the tricks one can do yet :)
I've effectively got a function:
void select_comparator(My_Struct *structure, int (*comp)(int x, int y)) {
...
...where My_Struct has prototype:
typedef struct my_struct {
int (*comp)(int x, int y);
} My_Struct;
Modulo some minor details. I just want to know if the following is correct syntax:
void select_comparator(My_Struct *structure, int (*comp)(int x, int y)) {
structure->comp = comp;
}
It seems almost too easy, and I'm worried it is.
Nothing's wrong: this is the basis of callbacks in c. Just make sure the signature of your function pointer matches the type defined in your structure. Where it gets remotely tricky is when you're using this in a large project, and people forget to check if the function pointer is valid or void, along with arguments, etc.
Code Listing
/*******************************************************************************
* Preprocessor directives.
******************************************************************************/
#include <stdio.h>
/*******************************************************************************
* Data types.
******************************************************************************/
typedef struct my_struct {
int (*comp)(int x, int y);
} My_Struct;
/*******************************************************************************
* Function prototypes.
******************************************************************************/
int c(int a, int b);
void select_comparator(My_Struct *structure, int (*comp)(int x, int y));
/*******************************************************************************
* Function definitions.
******************************************************************************/
/*----------------------------------------------------------------------------*/
int main(void)
{
My_Struct s;
select_comparator(&s, &c);
s.comp(1, 2);
return 0;
}
/*----------------------------------------------------------------------------*/
void select_comparator(My_Struct *structure, int (*comp)(int x, int y))
{
structure->comp = comp;
}
/*----------------------------------------------------------------------------*/
int c(int a, int b)
{
int ret = 0;
if (a < b) {
ret = (-1);
} else if (a > b) {
ret = 1;
}
return ret;
}
The code is ok.
Though note that function pointers have plain horrible syntax in C, particularly when passed to/returned from functions. Try writing something like "function returning function-pointer and taking function-pointer as parameter" and you'll soon realize that the syntax is pure madness.
It is therefore a good idea to make function pointers "fall in line" with the rest of the language by using typedefs.
You code could be written like this:
typedef int comp_t (int x, int y); // typedef a function type
typedef struct {
comp_t* comp; // pointer to such a function type
} My_Struct;
void select_comparator(My_Struct *structure, comp_t* comp) {
structure->comp = comp;
}
Now the code turns easier to read and the function pointer behaves pretty much like any other pointer.
I would like to be able to do something like this:
void test();
void (*testPointer)() = SomethingThatReturnsAFunctionPointer();
test = testPointer;
I would like to make something that functions similarly to the way openGL headers are implemented in which function prototypes are declared, and then the functions are set to a pointer. In other words, I would like to know how some openGL header files are able to both load the openGL functions, and have prototypes of the functions at the same time.
Functions are not variables; they cannot be assigned to.
However, functions can be implicitly converted to pointers to those functions. The function itself still isn't a variable, but you can assign that function pointer to a variable that is suitably typed for that function pointer.
I would like to know how some openGL header files are able to both load the openGL functions, and have prototypes of the functions at the same time.
I don't know which particular header you're talking about, but the loader I created simply has the implementation of the function call the function pointer, passing it all of the parameters and returning its value (if any). The pointer is defined inside a source file, so it's not in the header itself.
Using your example:
//header
void test();
//source file
void (*testPointer)();
void test()
{
testPointer();
}
You can even get fancy and make test load the pointer:
//source file
void (*testPointer)() == NULL;
void test()
{
if(!testPointer)
{
testPointer = SomethingThatReturnsAFunctionPointer();
}
testPointer();
}
1st:
int aplusb(int a, int b){return a + b;}
int aminusb(int a, int b){return a - b;}
int (*func)(int a, int b) = aplusb;
int some_func_caller ( int A, int B, int (*func)(int a, int b)){
return func(A, B);
}
int main(){
int a_ =10, b_ = 7;
int res1 = func(a_, b_);
int res2 = somefunc_caller(a_, b_, aminusb);
return 0;
}
2nd:
(if you re using c++ compiler)
typedef int MyFuncionType(int a, int b);
typedef int (*MyFuncionType2)(int a, int b);
int aplusb(int a, int b){return a + b;}
int aminusb(int a, int b){return a - b;}
int some_function_caller1(int a, int b, MyfunctionType fc){return fc(a,b);}
int some_function_caller2(int a, int b, MyfunctionType2 fc){return fc(a,b);}
int main(){
int a_ = 10, b_ = 7;
MyFunctionType *func1 = aminusb, *func2 = nullptr;
MyFunctionType2 func3 = aplusb, func4 = nullptr;
int res1 = func1(a_, b_);
int res2 = func3(a_, b_);
int res3 = some_function_caller1(a_, b_, aplusb);
int res4 = some_function_caller2(a_, b_, aminusb);
return 0;
}
My question is in general how to use pointers in functions correctly.
if to be more specific I need to write a function the recives 3 values from a user and then retruns it to the main one for further actions.
This is the code I have written so far:
#include <stdio.h>
#include <conio.h>
int inputThree(int, int, int);
int sortTwo(int, int);
int sortThree(int, int);
int main()
{
int a=0, b=0, c=0;
printf("before: func %d \n", b);
inputThree(a,b,c);
printf("after func: %d%d%d \n",a,b,c);
getch();
}
int inputThree(int a, int b, int c)
{
printf("Input three integers values: \n");
scanf("%d%d%d", &a, &b, &c);
return 0;
}
I'm intersted in understanding how to keep the values of scanf via pointers. When I return to the main function they are lost because they aren't global...
Also, I couldn't leave the function inputthree without parameters even though I want it to get them from scanf itself, so I had to put some values for it to run.
thanks in advance!
Pass pointers to the variables from main to inputThree.
Change the function declaration.
int inputThree(int* aPtr, int* bPtr, int* cPtr);
Change the call.
inputThree(&a, &b, &c);
Change the implementation.
int inputThree(int* aPtr, int* bPtr, int* cPtr)
{
printf("Input three integers values: \n");
scanf("%d%d%d", aPtr, bPtr, cPtr);
return 0;
}
You can either return a struct or make a function that handles passed pointers as argument.
#include <stdio.h>
struct Foo{
int x;
int y;
};
//one way
struct Foo do_work();
//or another
void do_work(int *x, int *y);
int main(void) {
return 0;
}
struct Foo do_work(){
//e.g.
struct Foo foo;
foo.x = 1;
foo.y = 2;
return foo;
}
void do_work1(int *x, int *y){
//e.g
*x = 1;
*y = 1;
}
Technically, only 1 thing (or none) can be returned from a function at a time. If you wanted to change the values of two or more variables via a function even after the function ends, you would need to pass into the function's parameters/arguments the memory reference of the variable.
I have a C++ program that shows an error:
too few arguments to function void split(char*, char**, int, int, int*)
Code:
#include <iostream>
#include <stdlib.h>
using namespace std;
void split(char* lin, char** word, int i, int w, int* c);
int main() {
char line[80] = "myline";
int n = 5;
char **word;
split(line, word, 1, 1); //Error is here.
return 0;
}
void split(char* lin, char** word, int i,int w, int* c)
{
//statements
}
Can anyone tell whats wrong?
The function split takes 5 arguments and no default argument. You try to call it with 4 arguments. That wont work.
The last two times you call split() you're calling it with only 4 arguments, as in one too few. If you'd like you can define it for 4 arguments as well, but currently this is not the case