如果我想要表达一个指向任意函数类型的函数指针的话,用:
typedef void (*Function)(void);
Function f = ...;
还是使用:
typedef void *(*Function)(void *);
Function f = ...;
又或者用别的什么方式呢?
1
catror 2019-06-17 19:38:50 +08:00 1
void* 就可以了
|
2
haozhang OP @catror 其实我感觉反正到时候调用函数还是需要强制类型转换的,这里 typedef 写什么都不会影响最终的函数调用= =
|
3
letianqiu 2019-06-17 19:53:56 +08:00
@haozhang 你的写法根本不能指向任意函数类型。C 里面只有 void *类型表示任意指针类型。你的第一个写法表示的是一个没有参数,没有返回值的函数的指针。第二个写的是一个接受一个指针参数,返回一个指针的函数的指针。
|
4
fcten 2019-06-17 20:01:33 +08:00
建议直接用 intptr_t 存,反正使用的时候都要强制转换
|
5
haozhang OP @letianqiu 强制类型转换就可以了啊,比如:
``` int a() { return 1; } Function f = (void (*)(void))a; ((int (*)(void))f)() // 返回 1 ``` void *是不能指向函数的。 |
6
haozhang OP 我二了,试了一下,void *就可以了,直接强制类型转换一下就可以了= =
int a() {return 1;} void *f = (void *)a; ((int (*)(void))f)(); // 返回 1 |
8
zaiyund 2019-06-17 20:08:00 +08:00
我觉得 catror 的说法靠谱
|
9
letianqiu 2019-06-17 20:11:34 +08:00
@haozhang void *是可以指向任意指针的,当然包括函数啊。C 里面本来也不存在范型的函数,所以调用的时候都要强制类型转换,void *足够了
|
13
letianqiu 2019-06-17 21:05:01 +08:00
https://isocpp.org/wiki/faq/pointers-to-members#cant-cvt-fnptr-to-voidptr
更正一下,C++下是不能把函数赋值给 void *类型的变量的。 |
14
wutiantong 2019-06-18 00:32:06 +08:00
@letianqiu 你没有给出正确的参考,因为 pointer to member function 是不同于 pointer to function 的
|
15
wutiantong 2019-06-18 00:36:11 +08:00
@letianqiu 事实上,C++里 pointer to function 是可以转成 void *的
|
16
wheeler 2019-06-18 00:53:22 +08:00 via iPhone 2
|
17
catror 2019-06-18 01:08:23 +08:00
@haozhang 本质上就是存一个地址值,你强转成任意类型都没问题,只要保证转回来还是一样的就行。建议不要直接用 void*,还是用 typedef 定义一个别名,这样即使遇到 16 楼的链接里提到的情况,修改一下定义就行。
|
19
iwong0exv2 2019-06-18 07:18:35 +08:00 via Android
请参考 dlsym (in Linux) or GetProcAddress (in Windows)
|
20
visionsmile 2019-06-18 08:18:31 +08:00
@catror #18 C++里成员函数指针和普通的指针不一样,在有些编译器实现里它本质是个结构,存放着真正的函数指针和对 this 的偏移值~
|
21
letianqiu 2019-06-18 09:05:47 +08:00
@wutiantong 你仔细去看我给出的链接里的例子。C++里将一个函数赋值给 void *类型的指针的结果是为定义的。楼下已经有人提到了,void *只能表示数据类的指针
|
22
zwhfly 2019-06-18 09:20:35 +08:00 1
各位,void * 类型是不能存储函数指针的。
https://stackoverflow.com/questions/5579835/c-function-pointer-casting-to-void-pointer 只谈 C。 按 C 标准,函数指针可以转换为另一种类型的函数指针,但调用时必须转换到原类型使用。C 标准不支持函数指针与 void 指针互转。 虽说现实中的大多数编译器支持与 void 指针互转,但这么写是不符合标准的,是不好的。 回答题主的问题,答案是两种都可以,但第二种没必要,第一种比较干净一点。 |
23
nanmian 2019-06-18 09:40:13 +08:00
1.void* 能不能存函数指针不知道....
2.单纯提个疑问,调用时的输入输出规则你怎么约定了? 这样堆栈很容易不平衡的导致程序崩溃的。我曾经在 VS2015_C 语言_Win32 Console_Debug 上测试过,把一种函数指针强转为另外一种指针然后传值调用,如果默认约定是调用者平衡堆栈还好,只是输入输出会取错值(若涉及写形式参数的话,还可能出现"越界访问"),程序不会崩溃。但如果是被调用者平衡堆栈的话,程序会因为堆栈平衡性检查出错而崩溃。 |
24
wutiantong 2019-06-18 10:34:50 +08:00
@letianqiu 是我 sb 了,其实我昨天打开你那个链接加载得太慢一直没出来页面内位置,然后从上往下翻到了一处讲 pointer to member function 能不能转 void *的,就以为是你给的地方。关于能不能转我好像也搞错了,不好意思哈。
|
25
haozhang OP 结贴,最终我使用了:typedef void (*Function )(void);Function f = ...;
|
27
12tall 2019-06-18 17:06:25 +08:00
void * 可以指向任意数据,但是在使用时一般需要类型转换成相应的类型才可以
|
29
12tall 2019-06-19 11:25:53 +08:00
@haozhang 谢谢提醒!
感觉 http://www.c-faq.com/ptrs/generic.html 这个回复更让人信服,不能保证正确的转换; StackOverflow 里面的情况感觉和 void * 关系不大。因为之前在调单片机中断时就遇到了有时候需要必要的延时(任意一条语句)才能正确执行,和这个问题很像(跑题了似乎 |