函数指针

原创 2007年10月08日 22:58:00

 Function pointers
Note: The syntax for all of this seems a bit exotic. It is. It confuses a lot of people, even C wizards. Bear with me.

It’s possible to take the address of a function, too. And like arrays, functions decay to pointers when their names are used. So if you wanted the address of, say, strcpy, you could say either strcpy or &strcpy. (&strcpy[0] won’t work for obvious reasons.)

When you call a function, you use an operator called the function call operator. The function call operator takes a function pointer on its left side.

In this example, we pass dst and src as the arguments on the interior, and strcpy as the function (that is, the function pointer) to be called:

enum { str_length = 18U }; Remember the NUL terminator! char src[str_length] = "This is a string.", dst[str_length]; strcpy(dst, src); The function call operator in action (notice the function pointer on the left side).

There’s a special syntax for declaring variables whose type is a function pointer.

char *strcpy(char *dst, const char *src); An ordinary function declaration, for reference char *(*strcpy_ptr)(char *dst, const char *src); Pointer to strcpy-like function strcpy_ptr = strcpy; strcpy_ptr = &strcpy; This works too strcpy_ptr = &strcpy[0]; But not this

Note the parentheses around *strcpy_ptr in the above declaration. These separate the asterisk indicating return type (char *) from the asterisk indicating the pointer level of the variable (*strcpy_ptr — one level, pointer to function).

Also, just like in a regular function declaration, the parameter names are optional:

char *(*strcpy_ptr_noparams)(char *, const char *) = strcpy_ptr; Parameter names removed — still the same type

The type of the pointer to strcpy is char *(*)(char *, const char *); you may notice that this is the declaration from above, minus the variable name. You would use this in a cast. For example:

strcpy_ptr = (char *(*)(char *dst, const char *src))my_strcpy;

As you might expect, a pointer to a pointer to a function has two asterisks inside of the parentheses:

char *(**strcpy_ptr_ptr)(char *, const char *) = &strcpy_ptr;

We can have an array of function-pointers:

char *(*strcpies[3])(char *, const char *) = { strcpy, strcpy, strcpy }; char *(*strcpies[])(char *, const char *) = { strcpy, strcpy, strcpy }; Array size is optional, same as ever strcpies[0](dst, src);

Here’s a pathological declaration, taken from the C99 standard. ‘[This declaration] declares a function f with no parameters returning an int, a function fip with no parameter specification returning a pointer to an int, and a pointer pfi to a function with no parameter specification returning an int.’ (6.7.5.3[16])

int f(void), *fip(), (*pfi)();

In other words, the above is equivalent to the following three statements:

int f(void); int *fip(); Function returning int pointer int (*pfi)(); Pointer to function returning int

But if you thought that was mind-bending, brace yourself…


--------------------------------------------------------------------------------

A function pointer can even be the return value of a function. This part is really mind-bending, so stretch your brain a bit so as not to risk injury.

In order to explain this, I’m going to summarise all the declaration syntax you’ve learned so far. First, declaring a pointer variable:

char *ptr;

This declaration tells us the pointer type (char), pointer level (*), and variable name (ptr). And the latter two can go into parentheses:

char (*ptr);

What happens if we replace the variable name in the first declaration with a name followed by a set of parameters?

char *strcpy(char *dst, const char *src);

Huh. A function declaration.

But we also removed the * indicating pointer level — remember that the * in this function declaration is part of the return type of the function. So if we add the pointer-level asterisk back (using the parentheses):

char *(*strcpy_ptr)(char *dst, const char *src);

A function pointer variable!

But wait a minute. If this is a variable, and the first declaration was also a variable, can we not replace the variable name in THIS declaration with a name and a set of parameters?

YES WE CAN! And the result is the declaration of a function that returns a function pointer:

char *(*get_strcpy_ptr(void))(char *dst, const char *src);

Remember that the type of a pointer to a function taking no arguments and returning int is int (*)(void). So the type returned by this function is char *(*)(char *, const char *) (with, again, the inner * indicating a pointer, and the outer * being part of the return type of the pointed-to function). You may remember that that is also the type of strcpy_ptr.

So this function, which is called with no parameters, returns a pointer to a strcpy-like function:

strcpy_ptr = get_strcpy_ptr();

Because function pointer syntax is so mind-bending, most developers use typedefs to abstract them:

typedef char *(*strcpy_funcptr)(char *, const char *); strcpy_funcptr strcpy_ptr = strcpy; strcpy_funcptr get_strcpy_ptr(void);

指针函数与函数指针--两个简单例子进行说明

一直都对两个概念有所混淆--指针函数与函数指针,下面我们通过两个例子来讲解一下 ------------------------------------------------------------...
  • u014131641
  • u014131641
  • 2016年04月09日 14:44
  • 2969

linux C编程(五)函数指针与函数调用

函数指针函数指针,首先是一个指针,只不过该指针指向的是函数,而不是变量。#include int max(int x,int y) { return (x>y)?x:y; } int main()...
  • u012177034
  • u012177034
  • 2016年08月25日 22:45
  • 1247

C#中的函数指针(转)

函数指针也叫指向函数的指针,它是为了提高函数的通用性而引入的。比较传统的方法是在函数中增加参数,通过增加的参数来判断到底要用什么函数,这样的缺点是灵活性差,为了支持多种方法要在函数中要写很多分支判断语...
  • dragoo1
  • dragoo1
  • 2016年11月05日 11:00
  • 2274

Go语言学习六:指针与传递到函数的指针

package main import ( "fmt" ) const MAX int = 3 func main() { var a int = 20 var ip *int /* 声明...
  • shawncheer
  • shawncheer
  • 2016年03月30日 20:23
  • 713

C/C++函数指针用法总结

C++函数指针 一函数指针介绍   函数指针指向某种特定类型,函数的类型由其参数及返回类型共同决定,与函数名无关。举例如下: int add(int nLeft,int nRight);//...
  • u013507368
  • u013507368
  • 2014年12月02日 16:48
  • 687

函数指针和函数指针数组及其应用

1. 函数指针 先来看一个简单的例子。 int a=3; void *p=&a; 这是一个基础的不能再基础的例子。相信学过指针的都能看得懂。P是一个指针,指向a。a 是一个整形变量。 函数指针和其类似...
  • yuexiang321
  • yuexiang321
  • 2016年09月25日 11:07
  • 1874

函数指针的作用以及好处

//函数指针使用的例子#include #include char * fun(char * p1,char * p2) {   int i = 0;   i = strcmp(p1,p2);...
  • windyblankboy
  • windyblankboy
  • 2016年08月21日 00:44
  • 1861

函数指针,指针函数,返回值为指针的函数

在学习C语言时,一个比较容易混淆的概念就是函数指针、指针函数、返回值为指针的函数。本文将对这三个概念进行区分。指针函数就是返回值为指针的函数,两个本质上是同一事物,只是叫法不同。函数指针就是一个指向函...
  • wangxufa
  • wangxufa
  • 2017年06月08日 21:23
  • 619

js中神奇的函数指针

js中的函数指针是一个神奇的东西 定义function check(){};对于上面这个函数,check(函数名)就是函数指针,check指向函数主体,如果alert(ckeck),那么弹出的信...
  • l7945685
  • l7945685
  • 2016年08月15日 10:16
  • 1867

函数指针的好处、作用

C中函数指针的作用   项目中用到了很多封装在struct中的函数指针,以前在MFC里面经常用到则个作为回调函数,还以为是微软设计的特色呢。在网上查了一下它的用法,做个总结。   1)提供调...
  • wujiangguizhen
  • wujiangguizhen
  • 2013年12月06日 00:29
  • 11882
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:函数指针
举报原因:
原因补充:

(最多只允许输入30个字)