Я столкнулся с одной проблемой при попытке обучения данных с помощью SVM. Я получаю несколько разных областей (набор связанных пикселей) от изображений лица, а области из глаз очень похожи, поэтому я хочу использовать моменты Ху для описания фигуры и SVM для обучения. Но SVM не работает должным образом, метод svm.predict оценивает впоследствии все как неглазый, более того, те же самые области, которые были помечены и использованы в фазе тренировки как глаз, оцениваются как неглазурованные. Характеристические данные состоят только из 7 моментов Hu. Я отправлю здесь несколько примеров исходного кода за мгновение, спасибо заранее :)
Дополнительная информация:
входное изображение: http://i.stack.imgur.com/GyLO0.png
Настройка базового svm для 1 изображения:
int image_regions = 10;
Mat training_mat(image_regions ,7,CV_32FC1); // 7 hu moments
Mat labels(image_regions ,1,CV_32FC1); // for labels 1 (eye) and -1 (non eye)
// computing hu moments
Moments moments2=moments(croppedImage,false);
double hu[7];
HuMoments(moments2,hu);
// putting them into svm traning mat
for (int k=0;k<huCounter;k++)
training_mat.at<float>(counter,k) = hu[k]; // counter is current number of region
if (isEye(...))
{
labels.at<float>(counter,0)=1.0;
}
else
{
labels.at<float>(counter,0)=-1.0;
}
//I use the following:
CvSVM svm;
CvSVMParams params;
params.svm_type = CvSVM::C_SVC;
params.kernel_type = CvSVM::LINEAR;
params.term_crit = cvTermCriteria(CV_TERMCRIT_ITER, 1000, 1e-6);
// ... do the above mentioned phase, and then:
svm.train(training_mat, labels, Mat(), Mat(), params);
Надеюсь, следующие предложения помогут вам.....
Самая простая задача - использовать алгоритм кластеризации и попытаться сгруппировать данные в два класса. Если такой алгоритм, как "k-mean", может справиться с задачей, поэтому сделать вещи сложными с помощью SVM и нейронных сетей. Я предлагаю вам использовать этот метод, потому что ваш векторный размер объекта имеет очень маленький размер (7 часов Hu Moments), а также количество образцов.
Выполните функцию "Нормализация" (указанная в пункте 4), чтобы убедиться, что значения падают в ограниченном диапазоне.
Проверьте: "Ваши данные действительно разделяемы?" Поскольку ваши данные малы, возьмите несколько образцов из положительных изображений и несколько образцов из негативных изображений и постройте векторы признаков. Если вы можете визуально увидеть разницу, то любой алгоритм обучения может выполнить эту работу за вас. Как я уже говорил, простые трюки могут сделать лучше, чем сложная математика.
Только если вы решили использовать SVM, вы должны знать следующее:
• Как я вижу из вашего кода, вы используете Linear SVM, может быть, ваши данные не разделяются линейным ядром. Попробуйте использовать некоторое многочленное ядро или другие ядра. Существует один вариант bool CvSVM :: train_auto в openCV, просто посмотрите.
• Попробуйте проверить, являются ли значения вектора признаков, которые вы получаете, правильными значениями или нет (убедитесь, что они не являются некоторыми значениями мусора).
• Также вы можете выполнить нормализацию функции "ZERO MEAN и UNIT VARIENCE", прежде чем использовать ее для обучения.
• Самое главное увеличить количество изображений для обучения, как положительно, так и отрицательно.
• И последнее, но не менее важное: SVM не волшебный, в конце концов он просто рисует линию между двумя наборами точек. Поэтому не ожидайте, что он будет классифицировать все, что вы даете ему в качестве входных данных.
Если ничего не работает "Просто улучшите технику извлечения объектов",