c++ - 如何使用 C++ 中的 C99 样式数组函数签名最好地调用函数

标签 c++ c

我正在用 C++ 编写一些代码,需要调用用 C99 编写的库。该库在其函数参数中使用带有 static 关键字的 C99 样式数组声明。即,这样:

void my_func(int n, int my_ints[static n]);

但是,当在我的 C++ 项目中包含该库的 header 时,编译器 (clang) 在使用 -pedantic 标志时会抛出警告:

> g++ -pedantic -c my_code.cpp
In file included from my_code.cpp:
./my_c_lib.h: warning: variable length arrays are a C99 feature [-Wvla-extension]
void my_func(int n, int my_ints[static n]);

在这种情况下调用 C 库的正确/最佳方法是什么?除了关闭 vla-extension 警告之外,是否有一些方法可以解决它而不涉及重写库的 header 或编写中间 C 包装器?

最小工作示例:

extern "C" {
    void my_func(int n, int my_ints[static n]);
}

int main()
{
    int* some_ints = new int[10];
    my_func(10, some_ints);
    delete[] some_ints;
    return 0;
}

最佳答案

事实是,C++ 根本没有像 C99 那样强大的 VLA,而且很可能永远也不会;将 VLA 包含到语言中所取得的进步受到如此严格的限制,以至于它们几乎毫无用处。

也就是说,您最好的选择可能是为您实际使用的库函数编写一些包装器,从而公开样式的接口(interface)

void my_func_wrap(int n, int* my_ints);

这些将在 C99 文件中实现,如下所示:

void my_func_wrap(int n, int* my_ints) {
    my_func(n, my_ints);
}

C 头文件和带有实现的文件都可以从您的库头文件中自动生成,因为更改几乎是微不足道的。现在,您可以从 C++ 代码中调用包装器,而不会出现任何类型冲突。


第二种可能的方法是编写脚本,从库 header 中剥离所有 [] 括号的内容,然后改用它。这将完美地工作,因为即使在 C99 中声明

void my_func_wrap(int n, int my_ints[static n]);

衰变成

void my_func_wrap(int n, int* my_ints);

这就是为什么我不需要在上面的包装函数中进行任何转换的原因(我知道这听起来很疯狂,但这是事实)。只是您的 C++ 编译器不喜欢第一个语法变体。

关于c++ - 如何使用 C++ 中的 C99 样式数组函数签名最好地调用函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34730518/

相关文章:

c - 如何静态链接动态链接另一个库的库?

c - 在C代码中打印底部带有*的倒三角形

c++ - 如何获取 EFI 系统分区的卷名?

c++ - 如何从子类的构造函数初始化父类的私有(private)成员

c++ - 如何从 map 到达数组的元素?

c - 使用 union 时 .c include 文件中出现多个错误

c - 从 C 语言中的 C 风格字符串获取位序列?

c++ - boost 中的Matlab gamfit等效函数

c++ - 参数传递机制?

c++ - 即使未选中复选框,也可以使用 DateTimePicker 控件检索日期