C/C++ 中的有状态库

问题描述 投票:0回答:1

我发布这个问题是因为我觉得我不理解有关 C/C++ 库的一些基本概念。

假设我们有一个名为 lib_c 的库,保存一些状态(例如静态全局变量)。假设还有另一个库 lib_b 使用 lib_c。

现在,我正在编写一个程序A,它同时需要lib_b和lib_c。有什么方法可以使 A 使用的 lib_c 与 lib_b 使用的 lib_c 不同(即获取静态全局变量的单独副本)?

为了更好地说明我的挫败感,请参阅以下代码示例。

这是“有状态库”,它只有 2 个静态全局变量:

c.h:

#ifndef C_H
#define C_H
void init_variables(int a, int b);
int get_a();
int get_b();
#endif

抄送:

#include "c.h"
static int a_ = 0, b_ = 0;
void init_variables(int a, int b) {
    a_ = a;
    b_ = b;
}
int get_a() { return a_; }
int get_b() { return b_; }

这是另一个使用有状态库的库:

b.h:

#ifndef B_H
#define B_H
void read_b();
#endif

b.c:

#include <stdio.h>
#include "b.h"
#include "c.h"
void read_b() {
    printf("As seen from b.c: %d, %d\n", get_a(), get_b());
}

这是我的代码,使用两个库:

a.c:

#include <stdio.h>
#include "b.h"
#include "c.h"

void read_a() {
    printf("As seen from a.c: %d, %d\n", get_a(), get_b());
}

int main() {
    init_variables(1, 2);
    read_a();
    read_b();
    return 0;
}

read_a() 和 read_b() 都读取静态全局变量 1 和 2 的相同内容!看来 lib_b 和我的代码没有获得这些静态全局变量的不同副本。

我尝试过使用普通 gcc 命令进行编译和使用 CMake 进行构建。看看我写的CMakeLists:

cmake_minimum_required(VERSION 3.22)

project(UnderstandStatefulLibs VERSION 1.0 LANGUAGES C)

# c.c -> lib_c
add_library(lib_c c.c)

# b.c + lib_c -> lib_b
add_library(lib_b b.c)
target_link_libraries(lib_b PRIVATE lib_c)

# a.c + lib_b + lib_c -> executable
add_executable(main a.c)
target_link_libraries(main PRIVATE lib_b lib_c)

欢迎有关此主题的任何澄清。我想知道是否有可能获得静态全局变量的单独副本,如果可以,如何获得。

非常感谢!

c compilation linker
1个回答
0
投票

通常,需要在内部存储某些状态的库会被实现,以便有一个“open_library()”调用,该调用分配包含状态的数据结构或类的新副本,并返回一个不透明句柄(例如,指向结构)。

在对库的所有其他调用中,用户必须提供句柄作为函数的第一个参数。

还应该有一个“close_library(handle) 调用,用于释放在“open_library()”中分配的状态结构。

用户看不到状态结构的内部,只能通过调用库中的函数并传递句柄来操作状态结构中包含的数据。

© www.soinside.com 2019 - 2024. All rights reserved.