OpenCV--SVM多分类问题
生活随笔
收集整理的這篇文章主要介紹了
OpenCV--SVM多分类问题
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
版權聲明:本文為博主原創文章,未經博主允許不得轉載。 https://blog.csdn.net/heroacool/article/details/50997024 <div class="markdown_views"><p>物體識別中經常遇到多分類器問題,svm是比較成熟和直接的想法。一般來說使用svm作為多分類器主要有以下思路:</p>
一對多(one-vs-all)。訓練時依次將目標類別作為正樣本,其余樣本作為負樣本,以此訓練n個svm。這個在Andrew Ng的Machine leaning的課上介紹過。
缺點:因為訓練集是1:N的情況,存在較大的bias,不是特別實用。
一對一(one-vs-one)。訓練時,任意兩類樣本之間訓練一個svm,則n類別,訓練出(n-1)n/2個svm。在runtime時,對一個未知樣本分類,則使用投票的法方法。libsvm即使用的該種方法。
缺點:類別多的時候,(n-1)n/2個支持向量機,計算代價大。
層次支持向量機。首先將所有類別分類為兩個子類,再將子類進一步劃分為兩個子類,直到單獨子類為止。好像一棵樹耶。具體請參考:劉志剛, 李德仁, 秦前清, 等. 支持向量機在多類分類問題中的推廣[J]. 2004.
DAG-SVMS。由Platt提出的決策導向的循環圖DDAG導出的,是針對“一對一”SVMS存在誤分、拒分現象提出的。請參考論文
簡單示例
#include <opencv2/core.hpp> #include <opencv2/imgproc.hpp> #include "opencv2/imgcodecs.hpp" #include <opencv2/highgui.hpp> #include <opencv2/ml.hpp> using namespace cv; using namespace cv::ml; Vec3b getRandomColor(){ RNG rng(clock()); return Vec3b(rng.next() % 255, rng.next() % 255, rng.next() % 255); } int main( int, char **) { // Data for visual representation int width = 512, height = 512; Mat image = Mat::zeros(height, width, CV_8UC3); // Set up training data int labels[ 4] = { 1, 2, 3, 4}; float trainingData[ 4][ 2] = { { 100, 10}, { 10, 500}, { 500, 10}, { 500, 500} }; Mat trainingDataMat( 4, 2, CV_32FC1, trainingData); Mat labelsMat( 4, 1, CV_32SC1, labels); // Train the SVM //! [init] Ptr<SVM> svm = SVM::create(); svm->setType(SVM::C_SVC); svm->setKernel(SVM::POLY); svm->setDegree( 1.0); svm->setTermCriteria(TermCriteria(TermCriteria::MAX_ITER, 100, 1e-6)); //! [init] //! [train] // svm->train(trainingDataMat, ROW_SAMPLE, labelsMat); // Ptr<TrainData> auto_train_data = TrainData::create(trainingDataMat, ROW_SAMPLE, labelsMat); // svm->trainAuto(auto_train_data); svm->train(trainingDataMat, ROW_SAMPLE, labelsMat); //! [train] // Show the decision regions given by the SVM //! [show] Vec3b green( 0, 255, 0), blue ( 255, 0, 0), red( 0, 0, 255),yellow( 0, 255, 255); for ( int i = 0; i < image.rows; ++i){ for ( int j = 0; j < image.cols; ++j){ Mat sampleMat = (Mat_< float>( 1, 2) << j,i); float response = svm->predict(sampleMat); double ratio = 0.5; if (response == 1) image.at<Vec3b>(i,j) = green *ratio; else if (response == 2) image.at<Vec3b>(i,j) = blue *ratio; else if(response == 3){ image.at<Vec3b>(i,j) = red *ratio; } else if(response == 4){ image.at<Vec3b>(i,j) = yellow *ratio; } } } int thickness = - 1; int lineType = 8; circle( image, Point( 100, 10), 5, Scalar( 0, 255, 0), thickness, lineType ); circle( image, Point( 10, 500), 5, Scalar( 255, 0, 0), thickness, lineType ); circle( image, Point( 500, 10), 5, Scalar( 0, 0, 255), thickness, lineType ); circle( image, Point( 500, 500), 5, Scalar( 0, 255, 255), thickness, lineType ); thickness = 2; lineType = 8; Mat sv = svm->getSupportVectors(); std::cout << sv << std::endl; for ( int i = 0; i < sv.rows; ++i){ const float* v = sv.ptr< float>(i); circle( image, Point( ( int) v[ 0], ( int) v[ 1]), 6, CV_RGB( 128, 128, 128), 2); } imwrite( "result.png", image); // save the image imshow( "SVM Simple Example", image); // show it to the user waitKey( 0); }- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 78
- 79
- 80
- 81
- 82
- 83
效果:
注意點:
使用RBF核或者使用autotrain,參數選擇十分重要。不行你試試喲!!!
總結
以上是生活随笔為你收集整理的OpenCV--SVM多分类问题的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 交换机组播风暴_广播风暴的成因以及解决办
- 下一篇: 已知多个同比增速和现期,快速比较多个对象