我想检测给定图像上的微笑,但是我得到一个错误的参数错误:
OpenCV Error: Incorrect size of input array (Input sample must be 1-dimensional vector) in cvPreparePredictData, file ..\..\..\..\opencv\modules\ml\src\inner_functions.cpp, line 1107
Exception in thread "main" CvException [org.opencv.core.CvException: cv::Exception: ..\..\..\..\opencv\modules\ml\src\inner_functions.cpp:1107: error: (-201) Input sample must be 1-dimensional vector in function cvPreparePredictData
]
在detectSmile(Mat face)方法的最后一行。整个代码:
public class SmileDetector {
private CascadeClassifier faceDetector;
private Mat image;
private Mat classes;
private Mat trainingData;
private Mat trainingImages;
private Mat trainingLabels;
CvSVM clasificador;
public void detectSmile(String filename) {
init();
detectFace(filename);
Mat face = Highgui.imread("output.png", Highgui.CV_LOAD_IMAGE_GRAYSCALE);
detectSmile(face);
}
private void init() {
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
faceDetector = new CascadeClassifier(new File(
"src/main/resources/haarcascade_frontalface_alt.xml").getAbsolutePath());
classes = new Mat();
trainingData = new Mat();
trainingImages = new Mat();
trainingLabels = new Mat();
}
private void detectFace(String filename) {
image = Highgui.imread(filename);
MatOfRect faceDetections = new MatOfRect();
faceDetector.detectMultiScale(image, faceDetections);
System.out.println(String.format("Detected %s faces", faceDetections.toArray().length));
for (Rect rect : faceDetections.toArray()) {
Core.rectangle(image, new Point(rect.x, rect.y), new Point(rect.x + rect.width, rect.y + rect.height),
new Scalar(0, 255, 0));
}
Highgui.imwrite("output.png", image.submat(faceDetections.toArray()[0]));
}
private void trainSVM() {
trainPositive();
trainNegative();
trainingImages.copyTo(trainingData);
trainingData.convertTo(trainingData, CvType.CV_32FC1);
trainingLabels.copyTo(classes);
}
private void trainPositive() {
Mat img = new Mat();
Mat con = Highgui.imread("D:\\cybuch\\workspace\\facerecognizer\\src\\main\\resources\\happy.png", Highgui.CV_LOAD_IMAGE_GRAYSCALE);
con.convertTo(img, CvType.CV_32FC1,1.0/255.0);
trainingImages.push_back(img.reshape(1, 1));
trainingLabels.push_back(Mat.ones(new Size(1, 1), CvType.CV_32FC1));
}
private void trainNegative() {
Mat img = new Mat();
Mat con = Highgui.imread("D:\\cybuch\\workspace\\facerecognizer\\src\\main\\resources\\sad.png", Highgui.CV_LOAD_IMAGE_GRAYSCALE);
con.convertTo(img, CvType.CV_32FC1,1.0/255.0);
trainingImages.push_back(img.reshape(1,1));
trainingLabels.push_back(Mat.zeros(new Size(1, 1), CvType.CV_32FC1));
}
private void detectSmile(Mat face) {
trainSVM();
CvSVMParams params = new CvSVMParams();
params.set_kernel_type(CvSVM.LINEAR);
clasificador = new CvSVM(trainingData, classes, new Mat(), new Mat(), params);
clasificador.save("svm.xml");
clasificador.load("svm.xml");
System.out.println(clasificador);
Mat out = new Mat();
face.convertTo(out, CvType.CV_32FC1);
out.reshape(1, 1);
System.out.println(out);
System.out.println(clasificador.predict(out));
}
}
我只使用一个训练图像样本,但我稍后会重写它。现在我只想让预测工作。
答案 0 :(得分:2)
reshape 返回另一个Mat,它无法就地。
所以,将代码更改为:
out = out.reshape(1, 1);
(或clasificador.predict(out.reshape(1,1)))
(不用担心,如果我每个人都有一分钱,他们会进入那个坑,我会变得富有)