Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/71.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 修改函数指针的签名_C_Function_Pointers - Fatal编程技术网

C 修改函数指针的签名

C 修改函数指针的签名,c,function,pointers,C,Function,Pointers,我遇到了一个小问题,我有一个函数指针: typedef void* (* funcPointer)(const void *in, int ilen, void *out, int *olen) 这个函数呢 void* foo1(const void *in, int ilen, void *out, int *olen) { if(CONST_VALUE_1 > iLen) //do something else //do something els

我遇到了一个小问题,我有一个函数指针:

typedef void* (* funcPointer)(const void *in, int ilen, void *out, int *olen)
这个函数呢

void* foo1(const void *in, int ilen, void *out, int *olen)
{
   if(CONST_VALUE_1 > iLen)
      //do something
   else
      //do something else
   return whatever;
}
代码中的某个地方

// ...
funcPointer fpointer = foo1;
if(someArgument > SOME_OTHER_CONSTANT)
   // where foo2 is the same as foo1 except that it uses CONST_VALUE_2
   fpointer = foo2; 
bar( someVariable, anotherVariable, fpointer);
// ...
如您所见,此函数体中有一个
CONST\u VALUE\u X
。我希望能够删除该常量并使用第五个参数。因为我不能修改签名,我想知道是否有什么事情要做,或者用每个可能的常量值复制粘贴函数


谢谢你

如果你不能修改函数签名,那么就像你说的,你就没有第五个参数了

我认为有三种选择:

  • 我想你可以把它塞进另一个
    void*
    参数中(例如,定义一个结构,其中包含
    的原始值和“常量”值,然后作为
    中的
    传递)

  • 在调用函数之前设置一个全局变量这是个坏主意。

  • 您可以将此函数编写为宏,以避免复制和粘贴维护的噩梦这是个坏主意。


  • 您可以将常量替换为调用者可以临时更改的内容(如全局变量)

    例如:

    int oldLenghtLimit = LengthLimit;
    ... call the function ...
    LengthLimit = oldLengthLimit;
    
    在函数中:

    void* foo1(const void *in, int ilen, void *out, int *olen)
    {
      if(LengthLimit > iLen)
        //do something
      else
        //do something else
      return whatever;
    }
    

    您想要的是一个闭包,而C并没有对闭包的显式支持。通过修改API以携带函数指针和参数指针,而不仅仅是函数指针,可以实现同样的效果。然后,您只需要查看函数的版本:一个使用显式调用者提供的参数,另一个使用携带的参数指针中的值。

    您可以控制传递到回调函数中的任何值吗?您可以包装它吗?为什么不创建一个接受第5个参数的基函数,然后从尊重签名的函数中调用它来传递CONST_VALUE_X?@TurqMage不,我对bar函数没有任何控制权也许这个C语言中的常用实现可以提供一些线索:听起来你可以修改
    foo1
    ,但不能修改它的签名(因为它必须通过函数指针被
    bar
    调用,并且您不能更改
    bar
    ).对吗?如果是这样,那么你可能应该用一个额外的参数定义一个函数
    foo
    ,然后让
    foo1
    CONST\u VALUE\u 1
    调用它,而
    foo2
    CONST\u VALUE\u 2
    调用它。这是在没有某种形式的闭包或部分函数应用程序的情况下所能做的最好的C缺乏。是的,这正是我所想的,但我希望有一个更好、更干净的解决方案。@Francis:我不确定你期望的是哪种解决方案!最好、最干净的解决方案是修改签名。如果你做不到这一点,你就只能得到上面提到的混乱解决方案。选项#1是最好的选择。C语言没有e你想要的高级功能,所以你必须自己发明。让你做你想做的事情的语言可能是“隐藏的”无论如何,它比预处理器宏或全局变量干净得多。当然,这只在我们知道调用方遵循该约定的情况下才有效。事实并非如此,因为调用后恢复了原始值,旧代码仍然有效(假设
    LengthLimit
    初始化为
    CONST\u VALUE\u 1
    )我的意思是,如果你把五个函数指针交给你无法控制的地方,那么这些指针就必须遵循这个惯例,否则它就不起作用了。