8#ifndef IGL_MATLAB_MATLAB_WORKSPACE_H
9#define IGL_MATLAB_MATLAB_WORKSPACE_H
12#include <Eigen/Sparse>
39 std::vector<std::string> names;
41 std::vector<mxArray*> data;
51 inline bool write(
const std::string & path)
const;
56 inline bool read(
const std::string & path);
65 template <
typename DerivedM>
67 const Eigen::MatrixBase<DerivedM>& M,
68 const std::string & name);
71 template <
typename MT>
73 const Eigen::SparseMatrix<MT>& M,
74 const std::string & name);
77 template <
typename ScalarM>
79 const std::vector<std::vector<ScalarM> > & vM,
80 const std::string & name);
83 template <
typename ScalarV>
85 const std::vector<ScalarV> & vV,
86 const std::string & name);
94 const Eigen::Quaternion<Q> & q,
95 const std::string & name);
99 const std::string & name);
103 template <
typename DerivedM>
105 const Eigen::DenseBase<DerivedM>& M,
106 const std::string & name);
109 template <
typename ScalarM>
111 const std::vector<std::vector<ScalarM> > & vM,
112 const std::string & name);
115 template <
typename ScalarV>
117 const std::vector<ScalarV> & vV,
118 const std::string & name);
127 template <
typename DerivedM>
129 const std::string & name,
130 Eigen::PlainObjectBase<DerivedM>& M);
133 template <
typename MT>
135 const std::string & name,
136 Eigen::SparseMatrix<MT>& M);
139 const std::string & name,
143 const std::string & name,
149 template <
typename DerivedM>
151 const std::string & name,
152 Eigen::PlainObjectBase<DerivedM>& M);
187 for_each(data.begin(),data.end(),&mxDestroyArray);
194 MATFile * mat_file = matOpen(path.c_str(),
"w");
197 fprintf(stderr,
"Error opening file %s\n",path.c_str());
200 assert(names.size() == data.size());
202 for(
int i = 0;i < (int)names.size(); i++)
205 int status = matPutVariable(mat_file,names[i].c_str(), data[i]);
208 std::cerr<<
"^MatlabWorkspace::save Error: matPutVariable ("<<names[i]<<
209 ") failed"<<std::endl;
213 if(matClose(mat_file) != 0)
215 fprintf(stderr,
"Error closing file %s\n",path.c_str());
226 mat_file = matOpen(path.c_str(),
"r");
227 if (mat_file == NULL)
229 std::cerr<<
"Error: failed to open "<<path<<std::endl;
234 const char ** dir = (
const char **)matGetDir(mat_file, &ndir);
236 std::cerr<<
"Error reading directory of file "<< path<<std::endl;
242 if(matClose(mat_file) != 0)
244 std::cerr<<
"Error: failed to close file "<<path<<std::endl;
247 mat_file = matOpen(path.c_str(),
"r");
248 if (mat_file == NULL)
250 std::cerr<<
"Error: failed to open "<<path<<std::endl;
256 for (
int i=0; i<ndir; i++)
259 mxArray * mx_data = matGetNextVariable(mat_file, &name);
262 std::cerr<<
"Error: matGetNextVariable failed in "<<path<<std::endl;
265 const int dims = mxGetNumberOfDimensions(mx_data);
269 fprintf(stderr,
"Variable '%s' has %d ≠ 2 dimensions. Skipping\n",
271 mxDestroyArray(mx_data);
275 names.push_back(name);
276 data.push_back(mx_data);
279 if(matClose(mat_file) != 0)
281 std::cerr<<
"Error: failed to close file "<<path<<std::endl;
289template <
typename DerivedM>
291 const Eigen::MatrixBase<DerivedM>& M,
292 const std::string & name)
294 const int m = M.rows();
295 const int n = M.cols();
296 mxArray * mx_data = mxCreateDoubleMatrix(m,n,mxREAL);
297 data.push_back(mx_data);
298 names.push_back(name);
301 Eigen::Map< Eigen::Matrix<double,Eigen::Dynamic,Eigen::Dynamic> >
302 map(mxGetPr(mx_data),m,n);
303 map = M.template cast<double>();
308template <
typename MT>
310 const Eigen::SparseMatrix<MT>& M,
311 const std::string & name)
313 const int m = M.rows();
314 const int n = M.cols();
316 assert(n==M.outerSize());
317 const int nzmax = M.nonZeros();
318 mxArray * mx_data = mxCreateSparse(m, n, nzmax, mxREAL);
319 data.push_back(mx_data);
320 names.push_back(name);
322 double * pr = mxGetPr(mx_data);
323 mwIndex * ir = mxGetIr(mx_data);
324 mwIndex * jc = mxGetJc(mx_data);
328 for(
int j=0; j<M.outerSize();j++)
332 for(
typename Eigen::SparseMatrix<MT>::InnerIterator it (M,j); it; ++it)
339 jc[M.outerSize()] = k;
344template <
typename ScalarM>
346 const std::vector<std::vector<ScalarM> > & vM,
347 const std::string & name)
351 return this->
save(M,name);
354template <
typename ScalarV>
356 const std::vector<ScalarV> & vV,
357 const std::string & name)
361 return this->
save(V,name);
366 const Eigen::Quaternion<Q> & q,
367 const std::string & name)
369 Eigen::Matrix<Q,1,4> qm;
374 return save(qm,name);
379 const std::string & name)
381 Eigen::VectorXd v(1);
386template <
typename DerivedM>
389 const Eigen::DenseBase<DerivedM>& M,
390 const std::string & name)
394 return this->
save(Mp1,name);
397template <
typename ScalarM>
399 const std::vector<std::vector<ScalarM> > & vM,
400 const std::string & name)
407template <
typename ScalarV>
409 const std::vector<ScalarV> & vV,
410 const std::string & name)
417template <
typename DerivedM>
419 const std::string & name,
420 Eigen::PlainObjectBase<DerivedM>& M)
422 const int i = std::find(names.begin(), names.end(), name)-names.begin();
423 if(i>=(
int)names.size())
427 assert(i<=(
int)data.size());
428 mxArray * mx_data = data[i];
429 assert(!mxIsSparse(mx_data));
430 assert(mxGetNumberOfDimensions(mx_data) == 2);
432 const int m = mxGetM(mx_data);
433 const int n = mxGetN(mx_data);
436 if(DerivedM::IsVectorAtCompileTime)
438 assert(m==1 || n==1 || (m==0 && n==0));
444 assert(mxGetNumberOfElements(mx_data) == M.size());
446 M = Eigen::Map< Eigen::Matrix<double,Eigen::Dynamic,Eigen::Dynamic> >
447 (mxGetPr(mx_data),M.rows(),M.cols()).cast<typename DerivedM::Scalar>();
451template <
typename MT>
453 const std::string & name,
454 Eigen::SparseMatrix<MT>& M)
456 const int i = std::find(names.begin(), names.end(), name)-names.begin();
457 if(i>=(
int)names.size())
461 assert(i<=(
int)data.size());
462 mxArray * mx_data = data[i];
464 if(mxGetNumberOfElements(mx_data) == 0)
469 assert(mxIsSparse(mx_data));
470 assert(mxGetNumberOfDimensions(mx_data) == 2);
472 const int m = mxGetM(mx_data);
473 const int n = mxGetN(mx_data);
477 double * pr = mxGetPr(mx_data);
478 mwIndex * ir = mxGetIr(mx_data);
479 mwIndex * jc = mxGetJc(mx_data);
480 vector<Eigen::Triplet<MT> > MIJV;
481 const int nnz = mxGetNzmax(mx_data);
485 for(
int j=0; j<n;j++)
488 while(k<(
int)jc[j+1])
491 assert((
int)ir[k]<m);
493 MIJV.push_back(Eigen::Triplet<MT >(ir[k],j,pr[k]));
498 M.setFromTriplets(MIJV.begin(),MIJV.end());
504 const std::string & name,
507 const int i = std::find(names.begin(), names.end(), name)-names.begin();
508 if(i>=(
int)names.size())
512 assert(i<=(
int)data.size());
513 mxArray * mx_data = data[i];
514 assert(!mxIsSparse(mx_data));
515 assert(mxGetNumberOfDimensions(mx_data) == 2);
517 assert(mxGetNumberOfElements(mx_data) == 1);
520 mxGetPr(mx_data)+mxGetNumberOfElements(mx_data),
526 const std::string & name,
529 const int i = std::find(names.begin(), names.end(), name)-names.begin();
530 if(i>=(
int)names.size())
534 assert(i<=(
int)data.size());
535 mxArray * mx_data = data[i];
536 assert(!mxIsSparse(mx_data));
537 assert(mxGetNumberOfDimensions(mx_data) == 2);
539 assert(mxGetNumberOfElements(mx_data) == 1);
542 mxGetPr(mx_data)+mxGetNumberOfElements(mx_data),
547template <
typename DerivedM>
549 const std::string & name,
550 Eigen::PlainObjectBase<DerivedM>& M)
Class which contains data of a matlab workspace which can be written to a .mat file and loaded from m...
Definition MatlabWorkspace.h:35
MatlabWorkspace & save_index(const Eigen::DenseBase< DerivedM > &M, const std::string &name)
Same as save() but adds 1 to each element, useful for saving "index" matrices like lists of faces or ...
MatlabWorkspace & save(const std::vector< std::vector< ScalarM > > &vM, const std::string &name)
This is an overloaded member function, provided for convenience. It differs from the above function o...
MatlabWorkspace & save_index(const std::vector< ScalarV > &vV, const std::string &name)
This is an overloaded member function, provided for convenience. It differs from the above function o...
bool write(const std::string &path) const
Save current list of variables.
Definition MatlabWorkspace.h:192
bool find(const std::string &name, Eigen::PlainObjectBase< DerivedM > &M)
Find a certain matrix by name.
Definition MatlabWorkspace.h:418
MatlabWorkspace & save(const std::vector< ScalarV > &vV, const std::string &name)
This is an overloaded member function, provided for convenience. It differs from the above function o...
bool read(const std::string &path)
Load list of variables from .mat file.
Definition MatlabWorkspace.h:221
MatlabWorkspace()
Definition MatlabWorkspace.h:173
MatlabWorkspace & save(const Eigen::SparseMatrix< MT > &M, const std::string &name)
This is an overloaded member function, provided for convenience. It differs from the above function o...
~MatlabWorkspace()
Definition MatlabWorkspace.h:179
bool find_index(const std::string &name, Eigen::PlainObjectBase< DerivedM > &M)
Subtracts 1 from all entries.
Definition MatlabWorkspace.h:548
MatlabWorkspace & save(const Eigen::MatrixBase< DerivedM > &M, const std::string &name)
Assign data to a variable name in the workspace.
MatlabWorkspace & save_index(const std::vector< std::vector< ScalarM > > &vM, const std::string &name)
This is an overloaded member function, provided for convenience. It differs from the above function o...
MatlabWorkspace & save(const Eigen::Quaternion< Q > &q, const std::string &name)
void clear()
Clear names and data of variables in workspace.
Definition MatlabWorkspace.h:185
Definition matlabinterface.h:38
void for_each(const Eigen::SparseMatrix< AType > &A, const Func &func)
FOR_EACH Call a given function for each non-zero (i.e., explicit value might actually be ==0) in a Sp...
Definition for_each.h:31
bool list_to_matrix(const std::vector< std::vector< T > > &V, Eigen::PlainObjectBase< Derived > &M)
Convert a list (std::vector) of row vectors of the same length to a matrix.
void find(const Eigen::SparseMatrix< T > &X, Eigen::DenseBase< DerivedI > &I, Eigen::DenseBase< DerivedJ > &J, Eigen::DenseBase< DerivedV > &V)
Find the non-zero entries and there respective indices in a sparse matrix.