2014-12-30 40 views
2

我想用features2d得出了兩點images.So之間良好匹配(不是所有的比賽)我用這個代碼片段:openCV4Android features2d錯誤

Mat gray1 = //image1 converted to gray 
Mat gray2 = //image2 converted to gray 

MatOfDMatch matches = new MatOfDMatch(); 
MatOfDMatch gm = new MatOfDMatch(); 

LinkedList<DMatch> good_matches = new LinkedList<DMatch>(); 
MatOfKeyPoint keypoints_object = new MatOfKeyPoint(); 
MatOfKeyPoint keypoints_scene = new MatOfKeyPoint(); 
Mat descriptors_object = new Mat(); 
Mat descriptors_scene = new Mat(); 
FeatureDetector fd = FeatureDetector.create(FeatureDetector.ORB); 

fd.detect(gray1, keypoints_object); 
fd.detect(gray2, keypoints_scene); 
// – Step 2: Calculate descriptors (feature vectors) 
DescriptorExtractor extractor = DescriptorExtractor 
.create(DescriptorExtractor.ORB); 

extractor.compute(gray1, keypoints_object, descriptors_object); 
extractor.compute(gray2, keypoints_scene, descriptors_scene); 
DescriptorMatcher matcher = DescriptorMatcher 
.create(DescriptorMatcher.BRUTEFORCE_HAMMING); 

matcher.match(descriptors_object, descriptors_scene, matches); 

double max_dist = 0; 
double min_dist = 100; 
List<DMatch> matchesList = matches.toList(); 

// – Quick calculation of max and min distances between keypoints 
for (int i = 0; i < descriptors_object.rows(); i++) { 
    Double dist = (double) matchesList.get(i).distance; 
    if (dist < min_dist) 
    min_dist = dist; 
    if (dist > max_dist) 
    max_dist = dist; 
} 

for (int i = 0; i < descriptors_object.rows(); i++) { 
    if (matchesList.get(i).distance <= 3 * min_dist) { 
     good_matches.addLast(matchesList.get(i)); 
    } 
} 

gm.fromList(good_matches); 

List<KeyPoint> keypoints_objectList = keypoints_object.toList(); 
List<KeyPoint> keypoints_sceneList = keypoints_scene.toList(); 

MatOfKeyPoint matOfObjectGoodKeyPoints = new MatOfKeyPoint(); 
MatOfKeyPoint matOfSceneGoodKeyPoints = new MatOfKeyPoint(); 
LinkedList<KeyPoint> listOfObjectGoodKeyPoints = new LinkedList<KeyPoint>(); 
LinkedList<KeyPoint> listOfSceneGoodKeyPoints = new LinkedList<KeyPoint>(); 
for (int i = 0; i < good_matches.size(); i++) { 
    listOfObjectGoodKeyPoints.addLast(keypoints_objectList 
    .get(good_matches.get(i).queryIdx)); 
    listOfSceneGoodKeyPoints.addLast(keypoints_sceneList 
    .get(good_matches.get(i).trainIdx)); 
} 
matOfObjectGoodKeyPoints.fromList(listOfObjectGoodKeyPoints); 
matOfSceneGoodKeyPoints.fromList(listOfSceneGoodKeyPoints); 

// feature and connection colors 
Scalar RED = new Scalar(255, 0, 0); 
// output image 
Mat outputImg = new Mat(); 
MatOfByte drawnMatches = new MatOfByte(); 
// this would draw good matches,but not works fine: 
Features2d.drawMatches(gray1, matOfObjectGoodKeyPoints, gray2, 
matOfSceneGoodKeyPoints, gm, outputImg, Scalar.all(-1), RED, 
drawnMatches, Features2d.NOT_DRAW_SINGLE_POINTS); 

但在運行時,出現此錯誤:

CvException ... features2d/src/draw.cpp:208: error: (-215) i2 >= 0 && i2 < static_cast(keypoints2.size())

代碼中出現什麼問題?

回答

2

問題是,你給過濾的列表(即matOfSceneGoodKeyPoints)到drawMatches()。但好匹配列表gm包含基於原始列表的索引。因此改爲

Features2d.drawMatches(gray1, keypoints_object, gray2, 
keypoints_scene, gm, outputImg, Scalar.all(-1), RED, 
drawnMatches, Features2d.NOT_DRAW_SINGLE_POINTS); 

而你有你想要的。所畫的比賽仍然限制在最好的比賽中,因爲只使用gm

+1

我編輯了你的答案。它工作正常! – hasanghaforian