将Matlab数组移植到C/C++中



我正在将一个matlab程序移植到C/C++。我有几个问题,但最重要的问题之一是:Matlab对任何维度的数组都一视同仁。假设我们有这样的函数,

function result = f(A, B, C)
result = A + 2 * B + C;

ABC可以是任何维度/大小的数组。我不是一个C/C++专业人员,但我想这不是一个简单的&一个想法是使用void指针将数组传递给函数。那么,我应该如何处理维度和数组操作(+/*(?另一个想法是使用C++类。我可能可以编写一个包含所有必需数组操作的模板类,如(*,+,<<,>>,…(。但我确信这将是一项令人筋疲力尽的工作。有人有更好的主意吗?是否有支持+和*运算符的简单/多维/单头文件/开源数组类?

您可以查看boost::ublas库。它支持向量、矩阵、线性代数等。

我建议使用Armadillo。这些文档甚至为Matlab用户提供了一个语法转换表。

我建议您使用C++类。当然,不要自己实现这些类。有人在这样的任务中做得很出色@达伦建议嘘::乌布拉。我推荐艾格。它的功能比公开发行版多得多,维护良好,支持大量编译器,性能接近,有时甚至比"英特尔MKL"等专有库更好。

由于没有一个答案对我有效,我自己上了课。这门课对我来说效果很好。但我很确定它不是这么设计的。它还可能导致内存泄漏。如果你发现它有问题,请给我留言。如果我制作了一个新版本,让答案对其他人有用,我会升级代码。顺便说一句,这个类现在适用于1、2和3维,但它可以很容易地扩展到任何数量的维。这是代码,

#ifndef XARRAY_H_INCLUDED
#define XARRAY_H_INCLUDED
#include <string>
#include <sstream>
#include <vector>
#include <assert.h>
using namespace std;
template <class T = double>
class XArray
{
    // Fields (keep data)
    int index_helper[10];
    // cells of the array
    vector<T> table;
    // dimensions of the array
    vector<int> dims;
public:
    XArray(){}
    XArray(unsigned int n, int *d)
    {
        dims.resize(n);
        int size = 1;
        for (unsigned int i = 0; i < n; i++) {
            size *= d[i];
            dims[i] = d[i];
        }
        table.resize(size);
    }
    XArray(unsigned int d1)
    {
        dims.resize(1);
        dims[0] = d1;
        table.resize(d1);
    }
    XArray(unsigned int d1, unsigned int d2)
    {
        dims.resize(2);
        dims[0] = d1;
        dims[1] = d2;
        table.resize(d1 * d2);
    }
    XArray(unsigned int d1, unsigned int d2, unsigned int d3)
    {
        dims.resize(3);
        dims[0] = d1;
        dims[1] = d2;
        dims[2] = d3;
        table.resize(d1 * d2 * d3);
    }
    XArray(const XArray<T>& xa)
    {
        this->table = xa.table;
        this->dims = xa.dims;
    }
    int dim(int i)
    {
        return dims[i];
    }
    int num_dims()
    {
        return dims.size();
    }
    T& operator()(int i)
    {
        index_helper[0] = i;
        return get_helper(1, index_helper);
    }
    T& operator()(int i, int j)
    {
        index_helper[0] = i;
        index_helper[1] = j;
        return get_helper(2, index_helper);
    }
    T& operator()(int i, int j, int k)
    {
        index_helper[0] = i;
        index_helper[1] = j;
        index_helper[2] = k;
        return get_helper(3, index_helper);
    }
    XArray<T> operator*(double m)
    {
        XArray<T> r = *this;
        for (unsigned int i = 0; i < table.size(); i++) {
            r.table[i] *= m;
        }
        return r;
    }
    XArray<T> operator/(double m)
    {
        XArray<T> r = *this;
        for (unsigned int i = 0; i < table.size(); i++) {
            r.table[i] /= m;
        }
        return r;
    }
    XArray<T> operator+(const XArray<T> &that)
    {
        assert(this->dims.size() == that.dims.size());
        for (unsigned int i = 0; i < dims.size(); i++) {
            assert(this->dims[i] == that.dims[i]);
        }
        XArray<T> r = *this;
        for (unsigned int i = 0; i < table.size(); i++) {
            r.table[i] += that.table[i];
        }
        return r;
    }
    XArray<T> operator-(const XArray<T> &that)
    {
        assert(this->dims.size() == that.dims.size());
        for (unsigned int i = 0; i < dims.size(); i++) {
            assert(this->dims[i] == that.dims[i]);
        }
        XArray<T> r = *this;
        for (unsigned int i = 0; i < table.size(); i++) {
            r.table[i] -= that.table[i];
        }
        return r;
    }
private:
    T& get_helper(unsigned int n, int *indices)
    {
        assert(n == dims.size());
        int multiplier = 1;
        int index = 0;
        for (unsigned int i = 0; i < n; i++) {
            //cerr << "index " << i << " out of range. Expected [0, " << dims[i] - 1
            //     << "] found " << indices[i] << endl;
            assert(indices[i] >= 0 && indices[i] < dims[i]);
            index += indices[i] * multiplier;
            multiplier *= dims[i];
        }
        return table[index];
    }
};
template <class T>
ostream &operator<<(ostream &stream, XArray<T> xa)
{
    int d = xa.num_dims();
    if(d == 1)
    {
        int n = xa.dim(0);
        for(int i = 0; i < n; i++)
        {
            stream << xa(i);
            if(i < n - 1)
            {
                stream << ", ";
            }
        }
    }
    else
    {
        stream << "XArray[";
        for(int i = 0; i < d; i++)
        {
            stream << xa.dim(i);
            if(i < d - 1)
            {
                stream << "x";
            }
        }
        stream << "]";
    }
    return stream;
}
#endif // XARRAY_H_INCLUDED

相关内容

  • 没有找到相关文章

最新更新