如何使用FFI将2D矢量从Rust传递到Fortran?

问题描述

我正在尝试将2d f64矢量(Vec )从Rust传递给Fortran函数。我正在使用.as_mut_ptr()将一维矢量与其他Fortran函数一起使用。

我不完全确定如何为此类示例发布一个最小的工作示例,但是我们开始:

extern "C" {
    fn fortran1_(
        vector: *mut f64,length1: *const uint32_t
    );

    fn fortran2_(
        vector: *mut f64,length1: *const uint32_t,length2: *const uint32_t
    );
}

pub fn fortran1(
    length1: u32
) -> Vec<f64>{
    let mut vector = vec![0_f64; length1];
    unsafe{
        fortran1_(
            vector.as_mut_ptr(),&length1)
    }
    return vector;
}

pub fn fortran2(
    length1: u32,length2: u32
)-> Vec<Vec<f64>>{
    let mut vector = vec![vec![0_f64; length1]; length2];
    unsafe{
        fortran2_(vector.as_mut_ptr(),&length1,&length2)
    }
    return vector;
}

谢谢

解决方法

您的锈病Vec<Vec<_>>表示形式与Fortran的标准数据模型之间存在许多不匹配。

Fortran希望将二维数组安排在f64的连续切片中,但是Vec<Vec<_>>将其每一行都放在单独的堆分配中。

Fortran索引从1开始,而Vec从0开始。

最好实现struct Fortran2d<T> { vec: Vec<T>,rows: usize,cols:usize,}并在模拟Fortran索引的方法上实现方法。我认为这样会减轻痛苦。

impl Fortran2d<T> {
    /// maps fortran style 2d index to internal vec index
    fn index(&self,c: usize,r: usize) -> usize {
        assert!(c > 0 && c <= self.cols);
        assert!(r > 0 && r <= self.rows);
        (c - 1) + (r - 1) * self.cols
   }
}

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...