static Mat asRowMatrix(InputArrayOfArrays src, int rtype, double alpha=1, double beta=0) { // make sure the input data is a vector of matrices or vector of vector if(src.kind() != _InputArray::STD_VECTOR_MAT && src.kind() != _InputArray::STD_VECTOR_VECTOR) { String error_message = "The data is expected as InputArray::STD_VECTOR_MAT (a std::vector<Mat>) or _InputArray::STD_VECTOR_VECTOR (a std::vector< std::vector<...> >)."; CV_Error(Error::StsBadArg, error_message); } // number of samples size_t n = src.total(); // return empty matrix if no matrices given if(n == 0) return Mat(); // dimensionality of (reshaped) samples size_t d = src.getMat(0).total(); // create data matrix Mat data((int)n, (int)d, rtype); // now copy data for(unsigned int i = 0; i < n; i++) { // make sure data can be reshaped, throw exception if not! if(src.getMat(i).total() != d) { String error_message = format("Wrong number of elements in matrix #%d! Expected %d was %d.", i, d, src.getMat(i).total()); CV_Error(Error::StsBadArg, error_message); } // get a hold of the current row Mat xi = data.row(i); // make reshape happy by cloning for non-continuous matrices if(src.getMat(i).isContinuous()) { src.getMat(i).reshape(1, 1).convertTo(xi, rtype, alpha, beta); } else { src.getMat(i).clone().reshape(1, 1).convertTo(xi, rtype, alpha, beta); } } return data; }
//------------------------------------------------------------------------------ // libfacerec::asColumnMatrix //------------------------------------------------------------------------------ Mat libfacerec::asColumnMatrix(InputArrayOfArrays src, int rtype, double alpha, double beta) { // make sure the input data is a vector of matrices or vector of vector if(src.kind() != _InputArray::STD_VECTOR_MAT && src.kind() != _InputArray::STD_VECTOR_VECTOR) { CV_Error(CV_StsBadArg, "The data is expected as InputArray::STD_VECTOR_MAT (a std::vector<Mat>) or _InputArray::STD_VECTOR_VECTOR (a std::vector< vector<...> >)."); } int n = (int) src.total(); // return empty matrix if no data given if(n == 0) return Mat(); // dimensionality of samples int d = src.getMat(0).total(); // create data matrix Mat data(d, n, rtype); // now copy data for(int i = 0; i < n; i++) { // make sure data can be reshaped, throw exception if not! if(src.getMat(i).total() != d) { string error_message = format("Wrong number of elements in matrix #%d! Expected %d was %d.", i, d, src.getMat(i).total()); CV_Error(CV_StsBadArg, error_message); } // get a hold of the current row Mat yi = data.col(i); // make reshape happy by cloning for non-continuous matrices if(src.getMat(i).isContinuous()) { src.getMat(i).reshape(1, d).convertTo(yi, rtype, alpha, beta); } else { src.getMat(i).clone().reshape(1, d).convertTo(yi, rtype, alpha, beta); } } return data; }
//------------------------------------------------------------------------------ // Eigenfaces //------------------------------------------------------------------------------ void Eigenfaces::train(InputArrayOfArrays _src, InputArray _local_labels) { if(_src.total() == 0) { String error_message = format("Empty training data was given. You'll need more than one sample to learn a model."); CV_Error(Error::StsBadArg, error_message); } else if(_local_labels.getMat().type() != CV_32SC1) { String error_message = format("Labels must be given as integer (CV_32SC1). Expected %d, but was %d.", CV_32SC1, _local_labels.type()); CV_Error(Error::StsBadArg, error_message); } // make sure data has correct size if(_src.total() > 1) { for(int i = 1; i < static_cast<int>(_src.total()); i++) { if(_src.getMat(i-1).total() != _src.getMat(i).total()) { String error_message = format("In the Eigenfaces method all input samples (training images) must be of equal size! Expected %d pixels, but was %d pixels.", _src.getMat(i-1).total(), _src.getMat(i).total()); CV_Error(Error::StsUnsupportedFormat, error_message); } } } // get labels Mat labels = _local_labels.getMat(); // observations in row Mat data = asRowMatrix(_src, CV_64FC1); // number of samples int n = data.rows; // assert there are as much samples as labels if(static_cast<int>(labels.total()) != n) { String error_message = format("The number of samples (src) must equal the number of labels (labels)! len(src)=%d, len(labels)=%d.", n, labels.total()); CV_Error(Error::StsBadArg, error_message); } // clear existing model data _labels.release(); _projections.clear(); // clip number of components to be valid if((_num_components <= 0) || (_num_components > n)) _num_components = n; // perform the PCA PCA pca(data, Mat(), PCA::DATA_AS_ROW, _num_components); // copy the PCA results _mean = pca.mean.reshape(1,1); // store the mean vector _eigenvalues = pca.eigenvalues.clone(); // eigenvalues by row transpose(pca.eigenvectors, _eigenvectors); // eigenvectors by column // store labels for prediction _labels = labels.clone(); // save projections for(int sampleIdx = 0; sampleIdx < data.rows; sampleIdx++) { Mat p = subspaceProject(_eigenvectors, _mean, data.row(sampleIdx)); _projections.push_back(p); } }
void cv::mixChannels(InputArrayOfArrays src, InputArrayOfArrays dst, const vector<int>& fromTo) { if(fromTo.empty()) return; int i, nsrc = (int)src.total(), ndst = (int)dst.total(); CV_Assert(fromTo.size()%2 == 0 && nsrc > 0 && ndst > 0); cv::AutoBuffer<Mat> _buf(nsrc + ndst); Mat* buf = _buf; for( i = 0; i < nsrc; i++ ) buf[i] = src.getMat(i); for( i = 0; i < ndst; i++ ) buf[nsrc + i] = dst.getMat(i); mixChannels(&buf[0], nsrc, &buf[nsrc], ndst, &fromTo[0], fromTo.size()/2); }
static Mat asRowMatrix(InputArrayOfArrays src, int rtype, double alpha=1, double beta=0) { // number of samples int n = (int) src.total(); // return empty matrix if no data given if(n == 0) return Mat(); // dimensionality of samples int d = (int)src.getMat(0).total(); // create data matrix Mat data(n, d, rtype); // copy data for(int i = 0; i < n; i++) { Mat xi = data.row(i); src.getMat(i).reshape(1, 1).convertTo(xi, rtype, alpha, beta); } return data; }
void descriptorExtractor::extract(InputArrayOfArrays inputimg, OutputArray feature, String feature_blob) { if (net_ready) { Blob<float>* input_layer = convnet->input_blobs()[0]; input_layer->Reshape(1, num_channels, input_geometry.height, input_geometry.width); /* Forward dimension change to all layers. */ convnet->Reshape(); std::vector<cv::Mat> input_channels; wrapInput(&input_channels); if (inputimg.kind() == 65536) {/* this is a Mat */ Mat img = inputimg.getMat(); preprocess(img, &input_channels); convnet->ForwardPrefilled(); /* Copy the output layer to a std::vector */ Blob<float>* output_layer = convnet->blob_by_name(feature_blob).get(); const float* begin = output_layer->cpu_data(); const float* end = begin + output_layer->channels(); std::vector<float> featureVec = std::vector<float>(begin, end); cv::Mat feature_mat = cv::Mat(featureVec, true).t(); feature_mat.copyTo(feature); } else {/* This is a vector<Mat> */ vector<Mat> img; inputimg.getMatVector(img); Mat feature_vector; for (unsigned int i = 0; i < img.size(); ++i) { preprocess(img[i], &input_channels); convnet->ForwardPrefilled(); /* Copy the output layer to a std::vector */ Blob<float>* output_layer = convnet->blob_by_name(feature_blob).get(); const float* begin = output_layer->cpu_data(); const float* end = begin + output_layer->channels(); std::vector<float> featureVec = std::vector<float>(begin, end); if (i == 0) { feature_vector = cv::Mat(featureVec, true).t(); int dim_feature = feature_vector.cols; feature_vector.resize(img.size(), dim_feature); } feature_vector.row(i) = cv::Mat(featureVec, true).t(); } feature_vector.copyTo(feature); } } else std::cout << "Device must be set properly using constructor and the net must be set in advance using loadNet."; };
void cv::mixChannels(InputArrayOfArrays src, InputArrayOfArrays dst, const vector<int>& fromTo) { if(fromTo.empty()) return; bool src_is_mat = src.kind() != _InputArray::STD_VECTOR_MAT && src.kind() != _InputArray::STD_VECTOR_VECTOR; bool dst_is_mat = dst.kind() != _InputArray::STD_VECTOR_MAT && dst.kind() != _InputArray::STD_VECTOR_VECTOR; int i; int nsrc = src_is_mat ? 1 : (int)src.total(); int ndst = dst_is_mat ? 1 : (int)dst.total(); CV_Assert(fromTo.size()%2 == 0 && nsrc > 0 && ndst > 0); cv::AutoBuffer<Mat> _buf(nsrc + ndst); Mat* buf = _buf; for( i = 0; i < nsrc; i++ ) buf[i] = src.getMat(src_is_mat ? -1 : i); for( i = 0; i < ndst; i++ ) buf[nsrc + i] = dst.getMat(dst_is_mat ? -1 : i); mixChannels(&buf[0], nsrc, &buf[nsrc], ndst, &fromTo[0], fromTo.size()/2); }
static void collectCalibrationData( InputArrayOfArrays objectPoints, InputArrayOfArrays imagePoints1, InputArrayOfArrays imagePoints2, Mat& objPtMat, Mat& imgPtMat1, Mat* imgPtMat2, Mat& npoints ) { int nimages = (int)objectPoints.total(); int i, j = 0, ni = 0, total = 0; CV_Assert(nimages > 0 && nimages == (int)imagePoints1.total() && (!imgPtMat2 || nimages == (int)imagePoints2.total())); cout << " Number of Frames: " << nimages << endl; for( i = 0; i < nimages; i++ ) { cout << endl << "Object Points: " << endl; printMatOBJ(objectPoints.getMat(i)); cout << endl << "Image Points: " << endl; printMatIMG(imagePoints1.getMat(i)); ni = objectPoints.getMat(i).checkVector(3, CV_32F); CV_Assert( ni >= 0 ); total += ni; } npoints.create(1, (int)nimages, CV_32S); objPtMat.create(1, (int)total, CV_32FC3); imgPtMat1.create(1, (int)total, CV_32FC2); Point2f* imgPtData2 = 0; if( imgPtMat2 ) { imgPtMat2->create(1, (int)total, CV_32FC2); imgPtData2 = imgPtMat2->ptr<Point2f>(); } Point3f* objPtData = objPtMat.ptr<Point3f>(); Point2f* imgPtData1 = imgPtMat1.ptr<Point2f>(); for( i = 0; i < nimages; i++, j += ni ) { Mat objpt = objectPoints.getMat(i); Mat imgpt1 = imagePoints1.getMat(i); ni = objpt.checkVector(3, CV_32F); int ni1 = imgpt1.checkVector(2, CV_32F); CV_Assert( ni > 0 && ni == ni1 ); npoints.at<int>(i) = ni; memcpy( objPtData + j, objpt.data, ni*sizeof(objPtData[0]) ); memcpy( imgPtData1 + j, imgpt1.data, ni*sizeof(imgPtData1[0]) ); if( imgPtData2 ) { Mat imgpt2 = imagePoints2.getMat(i); int ni2 = imgpt2.checkVector(2, CV_32F); CV_Assert( ni == ni2 ); memcpy( imgPtData2 + j, imgpt2.data, ni*sizeof(imgPtData2[0]) ); } } }
//------------------------------------------------------------------------------ // Fisherfaces //------------------------------------------------------------------------------ void Fisherfaces::train(InputArrayOfArrays src, InputArray _lbls) { if(src.total() == 0) { String error_message = format("Empty training data was given. You'll need more than one sample to learn a model."); CV_Error(Error::StsBadArg, error_message); } else if(_lbls.getMat().type() != CV_32SC1) { String error_message = format("Labels must be given as integer (CV_32SC1). Expected %d, but was %d.", CV_32SC1, _lbls.type()); CV_Error(Error::StsBadArg, error_message); } // make sure data has correct size if(src.total() > 1) { for(int i = 1; i < static_cast<int>(src.total()); i++) { if(src.getMat(i-1).total() != src.getMat(i).total()) { String error_message = format("In the Fisherfaces method all input samples (training images) must be of equal size! Expected %d pixels, but was %d pixels.", src.getMat(i-1).total(), src.getMat(i).total()); CV_Error(Error::StsUnsupportedFormat, error_message); } } } // get data Mat labels = _lbls.getMat(); Mat data = asRowMatrix(src, CV_64FC1); // number of samples int N = data.rows; // make sure labels are passed in correct shape if(labels.total() != (size_t) N) { String error_message = format("The number of samples (src) must equal the number of labels (labels)! len(src)=%d, len(labels)=%d.", N, labels.total()); CV_Error(Error::StsBadArg, error_message); } else if(labels.rows != 1 && labels.cols != 1) { String error_message = format("Expected the labels in a matrix with one row or column! Given dimensions are rows=%s, cols=%d.", labels.rows, labels.cols); CV_Error(Error::StsBadArg, error_message); } // clear existing model data _labels.release(); _projections.clear(); // safely copy from cv::Mat to std::vector std::vector<int> ll; for(unsigned int i = 0; i < labels.total(); i++) { ll.push_back(labels.at<int>(i)); } // get the number of unique classes int C = (int) remove_dups(ll).size(); // clip number of components to be a valid number if((_num_components <= 0) || (_num_components > (C-1))) _num_components = (C-1); // perform a PCA and keep (N-C) components PCA pca(data, Mat(), PCA::DATA_AS_ROW, (N-C)); // project the data and perform a LDA on it LDA lda(pca.project(data),labels, _num_components); // store the total mean vector _mean = pca.mean.reshape(1,1); // store labels _labels = labels.clone(); // store the eigenvalues of the discriminants lda.eigenvalues().convertTo(_eigenvalues, CV_64FC1); // Now calculate the projection matrix as pca.eigenvectors * lda.eigenvectors. // Note: OpenCV stores the eigenvectors by row, so we need to transpose it! gemm(pca.eigenvectors, lda.eigenvectors(), 1.0, Mat(), 0.0, _eigenvectors, GEMM_1_T); // store the projections of the original data for(int sampleIdx = 0; sampleIdx < data.rows; sampleIdx++) { Mat p = LDA::subspaceProject(_eigenvectors, _mean, data.row(sampleIdx)); _projections.push_back(p); } }
void check(InputArrayOfArrays a) { cout << a.total() << endl; Mat b = a.getMat(); }