在 Java 中使用 SWIG 处理返回指向结构数组的指针的 C 函数

2023-12-09

我试图找出需要进行哪些 SWIG 接口文件更改才能处理 getFoo 返回指向自定义结构数组 (sender_id_t) 的指针。没有任何特殊的 SWIG 接口代码,我只得到 Java 端的指针。如何将该指针转换为可以循环或迭代的对象(在 Java 中),以便获取每个 sender_id_t id 值?感谢任何建议。

C结构:

typedef unsigned char id_v1_t[32];
typedef id_v1_t id_t;
%rename (Sample) sender_id_t_;
struct sender_id_t_ {
    id_t       id;
    uint32_t   phy_idx;
};

C函数:

//This will return a pointer to an array of sender_id_t data.  The number of elements is retrieved from a separate call. 
sender_id_t* getFoo(resultset_t* resultset);

例外:

 [exec] test_wrap.c: In function `new_foo_array':
 [exec] test_wrap.c:785: error: invalid application of `sizeof' to incomplete type `sender_id_t_' 
 [exec] test_wrap.c: At top level:
 [exec] test_wrap.c:792: error: return type is an incomplete type
 [exec] test_wrap.c: In function `foo_array_getitem':
 [exec] test_wrap.c:793: error: invalid use of undefined type `struct sender_id_t_'
 [exec] test_wrap.c:793: error: dereferencing pointer to incomplete type
 [exec] test_wrap.c:793: warning: `return' with a value, in function returning void
 [exec] test_wrap.c: At top level:
 [exec] test_wrap.c:795: error: parameter `value' has incomplete type
 [exec] test_wrap.c: In function `foo_array_setitem':

最简单的解决方案根本不涉及编写任何 JNI - 实际上它是method 2。所以我所做的是使用卡瑞斯.i公开一个非常基本的接口,然后编写一点 Java 来制作public认为它更有用/直观。关键是你需要提供一种将数组知识汇集在一起​​的方法and它的长度。我整理了一个最小的完整示例来说明,它返回一个 Java 数组,但它同样可以用于ArrayList或任何您喜欢的收藏。

首先是一个头文件,具有紧凑的内联实现:

#ifndef TEST_H
#define TEST_H

struct Foo {
   int v;
};

inline static struct Foo *getFoo() {
  static struct Foo r[] = {{0},{1},{2}};
  return r;
}

inline static unsigned short numFoo() {
  return 3;
}

#endif

然后用以下内容包裹:

%module test

%{
#include "test.h"
%}

%include <carrays.i>
%array_functions(struct Foo, foo_array);

%rename(getFooImpl) getFoo;
%javamethodmodifiers getFoo() "private";
%javamethodmodifiers numFoo() "private";
%include "test.h"

%pragma(java) modulecode=%{
  public static Foo[] getFoo() {
    final int num = numFoo();
    Foo ret[] = new Foo[num];
    Foo result = getFooImpl();
    for (int i = 0; i < num; ++i) {
      ret[i] = foo_array_getitem(result, i);
    }
    return ret;
  }  
%}

我们在哪里重命名getFoo()从头文件中获取并使其与相应的numFoo() private,即实施细节。

使用这两个私有函数,我们可以编写一个真正的,public Foo[] getFoo(),调用这两个函数,然后将结果复制到已知大小的实际数组中。

我对此进行了测试:

public class main {
  public static void main(String[] argv) {
    System.loadLibrary("test");
    Foo[] foos = test.getFoo();
    System.out.println(foos[2].getV());
  }
}

在我看来,这个解决方案比相应的基于 JNI 的示例更干净 - 编写更简单,并且更难引入错误,这使得它更易于维护。任何JavaorC 程序员看到它就几乎可以明白发生了什么。就性能而言,它可能不会差太多,并且在某些关键路径上可能不会花费大量时间 - 如果基准测试显示这是一个问题,那么以后仍然很容易走上 JNI 道路。

为了完整地“制作它”private“方面您可能还想做类似的事情:

%javamethodmodifiers foo_array_getitem "private";
%ignore foo_array_setitem;
%ignore delete_foo_array;
%ignore new_foo_array;
%include <carrays.i>
%array_functions(struct Foo, foo_array);

隐藏由生成的所有函数%array_functions macro.

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在 Java 中使用 SWIG 处理返回指向结构数组的指针的 C 函数 的相关文章

随机推荐

  • 如何在用户表单列表框中显示过滤后的行

    我在用户窗体中有一个 Excel 工作表和一个列表框 当我通过单击用户窗体上的按钮来过滤工作表并更新列表框时 我会看到列表框中的所有行 我的意思是 listbox1 显示所有单元格 过滤器 无过滤器 我的更新列表框的代码 Private S
  • 组合框控件模板下拉按钮

    我想知道是否有人有一个示例 说明如何设置组合框的样式 模板以仅在默认初始状态下显示按钮 有点像功能区栏的 DropDownButton 库 我只希望用户能够单击按钮并列出组合框项目 做出选择后 它不会将所选项目保存在文本字段中 因为没有文本
  • h2o 模型列出每个特征的 dtypes

    有没有一种方法可以列出现有 h2o 模型的每个特征的预期数据类型 而无需查看训练数据 类似于的输出h2o frame types 但不查看训练数据 只查看模型对象 在本例中 我有一个已保存的模型文件 可以导入回 h2o 的通用类型 而不是
  • HTTPS 通信失败 ABAP

    我正在开发一个应连接到两个 Web 应用程序的应用程序 第一个 Web 应用程序已完成 http example com 不幸的是 第二个 Web 应用程序使用 HTTPS https example com 抛出这个错误 Http Com
  • Android java使用Comparable自定义排序

    Override public int compareTo final myRow another final int BEFORE 1 final int EQUAL 0 final int AFTER 1 if this another
  • 如何使用 matplotlib 在单个页面上绘制多个绘图?

    我编写了一次打开 16 个数字的代码 目前 它们都作为单独的图表打开 我希望他们在同一页面上打开所有内容 不是同一个图表 我想要在单个页面 窗口上显示 16 个独立的图表 此外 由于某种原因 numbins 和 defaultreallim
  • 按类别名称搜索

    当我尝试按类别名称进行搜索时 它什么也没有返回 例如 我有有机 独特 体育等类别 在搜索中我输入独特 但我没有得到任何结果 不幸的是 Magento 的默认搜索功能是产品搜索 并且仅限于该范围 当您搜索 Unique 时 它会查找产品名称
  • Reporting Services 表达式在某些情况下会出错

    在报告的摘要行中计算平均值时出现错误 我的表情是这样的 IIF SUM Fields column3 Value gt 0 Format DateAdd s SUM Fields column4 Value SUM Fields colum
  • 在pygame中检查歌曲是否播放完毕

    有什么方法可以判断 pygame 中的歌曲是否已播放完毕 这是代码 from tkinter import import pygame root Tk pygame init def play pygame mixer music load
  • Visual Studio 2010 局部变量历史记录

    我正在调试一个具有多个嵌套循环的进程 这些循环会更改几个不同的局部变量 我可以通过一次迭代一次来观看这些内容 但这非常乏味 而且我正在忘记自己的位置 我根本没有时间每次都记下每个变量 有没有办法可以查看局部变量的历史记录 一个插件 如果没有
  • 在 xsl 变量中存储 html 标签

    抱歉 如果这是一个愚蠢的问题 但是可以在 xsl 1 0 变量中存储和检索 HTML 片段吗 例如
  • 在 Vagrant 配置期间使用 Sed 将行追加到文件

    我目前正在使用Vagrant设置运行 Ubuntu 的开发机器 我想在我的中添加几行 profile将目录添加到我的 PATH变量 使用sed 为此 我将这些行添加到我的机器中Vagrantfile config vm provision
  • 左值整型常量表达式是常量表达式吗?

    N4527 5 20 表达式常量 p3 An 积分常量表达式是整型或无范围枚举类型的表达式 隐式转换为纯右值 其中转换后的表达式是核心常量表达式 5 20 expr const p5 A 常量表达式是一个泛左值核心常量表达式 其值引用作为常
  • 为什么 Rust 不允许可变别名?

    Rust 不允许这种代码 因为它不安全 fn main let mut i 42 let ref to i 1 unsafe mut mut i as mut i32 let ref to i 2 unsafe mut mut i as m
  • 从给定 X 值的密度函数检索 Y 值

    给定一个简单的密度直方图和曲线 如下所示 如何检索给定 X 值的 Y 值 例如 y 值位于mean dat dat lt c 5 7 4 6 4 3 55 6 7 5 4 3 33 44 5 2 33 22 hist dat freq F
  • currentUser 返回 null

    我有一个使用 firebase auth 进行身份验证的反应应用程序 当一个人登录后 它会将他们重定向到书籍页面 这是提交登录处理程序 import auth firebase from firebase async function go
  • 如何使用 SMOTE 将合成数据集保存在 CSV 文件中

    我使用信用卡数据通过 SMOTE 进行过采样 我正在使用 geeksforgeeks org 中编写的代码 Link 运行以下代码后 它会显示类似以下内容 print Before OverSampling counts of label
  • 字符串周日期到冷融合日期

    我需要格式化一个字符串日期 如下所示 2021 W46 变成我可以在冷融合中使用的东西parseDateTime or dateFormat功能 W46在本例中是第 46 周 我尝试的是直接将该字符串放入parseDateTime and
  • Java并发——发布不可变对象(Java并发实践)

    在 Java Concurrency In Practice 一书中 作者指出 不可变对象可以通过任何机制发布 任何线程都可以安全地使用不可变对象 无需额外的同步 即使不使用同步来发布它们也是如此 这是否意味着以下习惯用法可以安全地发布不可
  • 在 Java 中使用 SWIG 处理返回指向结构数组的指针的 C 函数

    我试图找出需要进行哪些 SWIG 接口文件更改才能处理 getFoo 返回指向自定义结构数组 sender id t 的指针 没有任何特殊的 SWIG 接口代码 我只得到 Java 端的指针 如何将该指针转换为可以循环或迭代的对象 在 Ja