如何通过C++ MEX函数在MATLAB命令行窗口显示输出内容?
在MATLAB中显示C++ MEX函数的输出
C++ MEX函数中使用std::cout的输出不会直接显示在MATLAB命令窗口,因为两者的标准输出流相互独立。以下是几种可行的解决方案:
方法1:使用MATLAB C++ API直接输出(推荐)
通过MATLAB提供的API调用MATLAB原生的输出函数,替代std::cout,这是最直接且稳定的方式。
修改Helper类(允许修改原类时)
#ifndef HELPER_H #define HELPER_H #include "mex.hpp" #include "mexAdapter.hpp" class Helper { public: Helper(matlab::engine::MATLABEngine& matlabEngine) { // 调用MATLAB的disp函数输出字符串 matlabEngine.feval(u"disp", 0, std::vector<matlab::data::Array>({ matlab::data::CharArrayFactory().createCharArray("Hello World") })); } }; #endif
对应MEX函数修改
#include "mex.hpp" #include "mexAdapter.hpp" #include "Helper.h" class MexFunction : public matlab::mex::Function { private: std::shared_ptr<matlab::engine::MATLABEngine> matlabPtr = getEngine(); public: void operator()(matlab::mex::ArgumentList outputs, matlab::mex::ArgumentList inputs) { Helper helper(*matlabPtr); } };
方法2:重定向std::cout到MATLAB输出流
如果无法修改Helper类,可通过自定义缓冲区重定向std::cout的输出,将内容转发到MATLAB命令窗口。
#include "mex.hpp" #include "mexAdapter.hpp" #include "Helper.h" #include <iostream> #include <streambuf> // 自定义缓冲区类,转发输出到MATLAB class MatlabStreamBuf : public std::streambuf { private: std::shared_ptr<matlab::engine::MATLABEngine> matlabPtr; protected: int_type overflow(int_type c) override { if (c != EOF) { std::string s(1, static_cast<char>(c)); matlabPtr->feval(u"disp", 0, std::vector<matlab::data::Array>({ matlab::data::CharArrayFactory().createCharArray(s) })); } return c; } std::streamsize xsputn(const char* s, std::streamsize n) override { std::string str(s, n); matlabPtr->feval(u"disp", 0, std::vector<matlab::data::Array>({ matlab::data::CharArrayFactory().createCharArray(str) })); return n; } public: MatlabStreamBuf(std::shared_ptr<matlab::engine::MATLABEngine> ptr) : matlabPtr(ptr) {} }; class MexFunction : public matlab::mex::Function { private: std::shared_ptr<matlab::engine::MATLABEngine> matlabPtr = getEngine(); std::streambuf* originalCoutBuf; MatlabStreamBuf matlabStreamBuf; public: MexFunction() : matlabStreamBuf(matlabPtr) { // 替换std::cout的缓冲区 originalCoutBuf = std::cout.rdbuf(&matlabStreamBuf); } ~MexFunction() { // 恢复原缓冲区 std::cout.rdbuf(originalCoutBuf); } void operator()(matlab::mex::ArgumentList outputs, matlab::mex::ArgumentList inputs) { Helper(); // 此时std::cout输出会转发到MATLAB } };
方法3:捕获std::cout输出后一次性输出
将std::cout的输出临时捕获到字符串流中,再统一输出到MATLAB。
#include "mex.hpp" #include "mexAdapter.hpp" #include "Helper.h" #include <iostream> #include <sstream> #include <streambuf> class MexFunction : public matlab::mex::Function { private: std::shared_ptr<matlab::engine::MATLABEngine> matlabPtr = getEngine(); public: void operator()(matlab::mex::ArgumentList outputs, matlab::mex::ArgumentList inputs) { // 保存原std::cout缓冲区 std::streambuf* originalBuf = std::cout.rdbuf(); std::ostringstream oss; std::cout.rdbuf(oss.rdbuf()); // 调用Helper,输出被捕获到oss中 Helper(); // 恢复原缓冲区 std::cout.rdbuf(originalBuf); // 输出捕获的内容到MATLAB std::string outputStr = oss.str(); if (!outputStr.empty()) { matlabPtr->feval(u"disp", 0, std::vector<matlab::data::Array>({ matlab::data::CharArrayFactory().createCharArray(outputStr) })); } } };
内容的提问来源于stack exchange,提问作者Hadi_IronSide
相关产品推荐
相关产品推荐

