2

C++ から MATLAB を実行し、MATLAB 出力を構造体で C++ に戻そうとしています。構造体には、さまざまな次元や長さの配列など、いくつでも含めることができます。hereに同様の質問がありますが、答えは私が理解して推定するのに十分な詳細を提供しません.

MatlabEngine.hppとを使用して MATLAB を実行していMatlabDataArray.hppます。私は多くの出力を返す必要があり、私が求めていることを完全に実行しない他の方法を試しました。構造を使用することは、物事を行うための最も論理的で読みやすい方法のようです。以下の例で私のケースを説明しようと思います。これらの例は、同様の問題を抱えている他の人にとって最も役立つ方法で書かれていることを願っています.

MWE 1 - n x n 配列を返す

MATLAB コード
function output = simple_fun1(a, bc)
% Takes input values of a and an array [a,b]
b = bc(1);
c = bc(2);
sum = a+b+c;
prod = a*b*c;
output = [sum, prod; 3, 4];

これは、C++ コードを使用して実行できます。

C++ コード
#include "MatlabEngine.hpp"
#include "MatlabDataArray.hpp"
#include <iostream>

int main()
{
  using namespace matlab::engine;
  matlab::data::ArrayFactory factory; // Create MATLAB data array factory

  std::unique_ptr<MATLABEngine> matlabPtr = startMATLAB(); // Start MATLAB engine

  matlabPtr->eval(u"addpath(genpath('C:/Users/...your path here...'))"); // Add the path to where MATLAB functions are.

  std::vector<double> bc{ 10, 13};
  std::vector<matlab::data::Array> args({
    factory.CreateScalar<double>(7),
    factory.CreateArray({ 1, 2 }, bc.cbegin(), bc.cend())
  });
  
  matlab::data::TypedArray<double> results = matlabPtr->feval(u"simple_fun1",args); // Run simple_fun1
  
  std::cout << "Sum: " << results[0][0] << std::endl;
  std::cout << "Prod: " << results[0][1] << std:endl;
  std::cout << "Three: " << results[1][0] << std::endl;
}

これは、n x n 配列の単一の戻り値に対して機能します。しかし、データを個別に返したい場合、つまりfunction [sum, prod] = simple_fun1(a,bc)機能しません。

MWE2 - 複数の出力を返す

タプルを使用して複数の出力を返すことができましたが、MATLAB 配列のタプルを定義できなかったため、配列の最初の要素 (配列出力の場合) にしかアクセスできません。例えば

MATLAB コード
function [sum, prod] = simple_fun2(a, bc)
% Takes input values of a and an array [a,b]
b = bc(1);
c = bc(2);
sum = a+b+c;
prod = a*b*c;
C++ コード
  std::tuple<double, double> results;
  results = matlabPtr->feval< std::tuple<double, double>>(u"simple_fun2", double(7), std::vector<double>{ 10, 13}); // Just as another example of how to enter inputs in case that's helpful for anyone.
  double s;
  double p;
  std::tie(s, p) = results;
  std::cout << "Sum: " << s << ", Prod: " << p << std::endl;

リターン構造

代わりに、構造体を返すように MATLAB 関数を書きたいと思います。これにより、大量のデータが渡されるコードが簡素化され、データが異なる次元を持つことができるようになるはずです。ただし、実際の例を作成できませんでした。

MATLAB コード
function output = simple_fun3(a, bc)
b = bc(1);
c = bc(2);
output.sum = a+b+c;
output.prod = a*b*c;
output.a_sq = a*a;
output.b_sq = b*b;
C++ コード
#include "MatlabEngine.hpp"
#include "MatlabDataArray.hpp"
#include <iostream>

int main()
{
  using namespace matlab::engine;
  matlab::data::ArrayFactory factory; // Create MATLAB data array factory

  std::unique_ptr<MATLABEngine> matlabPtr = startMATLAB(); // Start MATLAB engine

  matlabPtr->eval(u"addpath(genpath('C:/Users/...your path here...'))"); // Add the path to where MATLAB functions are.

  std::vector<double> bc{ 10, 13};
  std::vector<matlab::data::Array> args({
    factory.CreateScalar<double>(7),
    factory.CreateArray({ 1, 2 }, bc.cbegin(), bc.cend())
  });
  
  matlab::data::StructArray my_matlab_struct = factory.createStructArray(matlab::data::ArrayDimensions{ 1, 4}, std::vector<std::string>{'sum', 'prod', 'a_sq', 'b_sq'});
  my_matlab_struct = matlabPtr->feval(u"simple_fun3",args);

上記の C++ コードは機能せず、構造がどのように定義されているかわかりません。つまり、ArrayDimensions の次元です。どんな助けでも大歓迎です。ありがとう

4

1 に答える 1