【问题标题】:Call functions from outside a static library in C从 C 中的静态库外部调用函数
【发布时间】:2019-03-05 08:58:26
【问题描述】:

我需要生成一个包含未实现函数的静态库 MyLib.lib。

在项目内部,我调用了未实现的函数,如下图:

/* Inside MyLib.c */

#include "MyLib.h"

void foo(void)
{
   func(); // To be implemented by the user.
}

在头文件 MyLib.h 中,我包含了一个头文件

#include "user.h" // contains user_imlplementation_of_func()

...


#define func()         user_imlplementation_of_func()

为了简单起见,我们只举一个user.c的例子:

void user_imlplementation_of_func(void)
{
   printf("OK");
}

我想知道是否可以打这个电话?否则,是否有任何其他解决方案可以在静态库中使用未实现的函数,并让用户在将项目从源代码压缩到 .lib 文件后定义它们

【问题讨论】:

  • 静态库实际上只不过是目标文件的集合。因此调用“从静态库外部的函数”与从其他目标文件调用函数是一样的。
  • 您可能希望将用户定义的函数作为回调传递给您的库,请查看stackoverflow.com/questions/142789/…
  • @Someprogrammerdude 如果我错了请纠正我:如果用户在他的项目中包含该库并且忘记添加#define func() user_imlplementation_of_func(),他会遇到编译问题。如果他添加定义,一切都会好起来的?
  • 根据您的编译器,您可以实现默认的“弱”功能,如果用户想要自己的功能,他可以简单地“覆盖”它。

标签: c


【解决方案1】:

您需要在库的标头中将未实现的函数声明为extern。这告诉编译器,该函数将在其他地方定义。

例子:

MyLib.h

void foo();

extern void func();

MyLib.c

#include "MyLib.h"

void foo(void)
{
    func();
}

main.c

#include <stdio.h>
#include "MyLib.h"

void func()
{
    printf("Hello, world!\n");
}

int main()
{
    foo();
}

示例构建:

cc -o MyLib.o -c MyLib.c
cc -o out main.c MyLib.o

输出:

$ ./out
Hello, world!

但是,为了提高可读性,我建议您将项目函数作为指向库函数的指针传递。这通常称为callback

例子:

/* MyLib.c */

#include "MyLib.h"

void foo(void (*func)(void))
{
   func();
}

现在您可以在项目中调用 foo 函数:

foo(&user_imlplementation_of_func);

编辑:

正如用户theSealion 在 cmets 中所述,第三种解决方案是使用弱符号。 The wikipedia articel "Weak symbol" 提供了很好的示例解释。

【讨论】:

    【解决方案2】:

    你可以做点别的——函数指针:

    //youLib.c
    
    extern void (*func)(void) = NULL;
    
    extern void foo()
    {
        if (func != NULL) {
            func();
        }
    }
    
    //main.c
    
    static void user_imlplementation_of_func(void)
    {
        printf("Hello\n");
    }
    
    func = &user_imlplementation_of_func;
    foo(); //Will printf "Hello"
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多