일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
- SERIAL
- Encapusulation
- sensor
- file access
- digitalRead
- compare
- UNO
- Class
- preprocessing
- wpf
- flutter
- Barcode
- Pointer
- atmega328
- mfc
- APP
- stream
- inheritance
- Contour
- aduino
- java
- Android
- parameter
- Read
- Binary
- public
- Overloading
- Unity
- memory
- length
- Today
- Total
폴크(FOLC)
머신 비전 알고리즘 - OpenCV - 이미지처리29 본문
# 디지털 이미지 처리
# 이미지의 상태 정보에서 일반적인 정보를 생성한다.
> 추출된 정보를 일반화한다.
# 이미지 처리 - OpenCV 4.5.3 으로 테스트
# 이미지의 상태 정보에서 일반적인 정보를 생성
> Points : 입력, model : 결과, distance : 노이즈로 판단하는 경계값
# RANSAC ( Random sample consensus )
> vector<cv::Point2f> vecData;
> CFitLineRANSAC ransac;
> cv::Vec4f model;
> ransac.FitLine(vecData, 3.0, model);
* 소스 코드 세부 내용 *
double CFitLineRANSAC::FitLine(const vector<cv::Point2f> &src, double distance_threshold, cv::Vec4f &result_model)
{
const int source_count = (int)src.size();
const int sample_count = 2;
if (source_count < sample_count)
{
return 0.0;
}
const int total_iter_count = (int)(1 + log(1.0 - 0.99) / log(1.0 - pow(0.5, sample_count)));
vector<cv::Point2f> vecSamples(sample_count);
double max_cost = 0.0;
for (int i = 0; i < total_iter_count; i++)
{
GetSampleToCompute(src, vecSamples);
cv::Vec4f estimated_model;
ComputeModelParameter(vecSamples, estimated_model);
vector<cv::Point2f> vecInliers;
const double cost = VerificationLineModel(estimated_model, distance_threshold, src, vecInliers);
if (max_cost < cost)
{
max_cost = cost;
ComputeModelParameter(vecInliers, result_model);
}
}
return max_cost;
}
void CFitLineRANSAC::GetSampleToCompute(const vector<cv::Point2f> &src, vector<cv::Point2f> &dst)
{
srand(RAND_MAX);
const int source_count = (int)src.size();
vector<int> vecIndex;
while(true)
{
const int random_index = rand() % source_count;
if(find(vecIndex.begin(), vecIndex.end(), random_index) == vecIndex.end())
{
vecIndex.push_back(random_index);
}
if (vecIndex.size() == dst.size())
{
for (size_t i = 0; i < dst.size(); ++i)
{
dst[i] = src[vecIndex[i]];
}
return;
}
}
}
void CFitLineRANSAC::ComputeModelParameter(const vector<cv::Point2f> &src, cv::Vec4f &model)
{
double sx = 0, sy = 0;
double sxx = 0, syy = 0;
double sxy = 0, sw = 0;
for(size_t i = 0; i < src.size(); ++i)
{
const double &x = src[i].x;
const double &y = src[i].y;
sx += x;
sy += y;
sxx += x * x;
sxy += x * y;
syy += y * y;
sw += 1;
}
const double vxx = (sxx - sx * sx / sw) / sw;
const double vxy = (sxy - sx * sy / sw) / sw;
const double vyy = (syy - sy * sy / sw) / sw;
const double theta = atan2(2.0 * vxy, vxx - vyy) / 2.0;
model[0] = (float)cos(theta);
model[1] = (float)sin(theta);
model[2] = (float)(sx / sw);
model[3] = (float)(sy / sw);
}
double CFitLineRANSAC::ComputeDistancePoint(const cv::Vec4f &line, const cv::Point2f &x)
{
const double det = sqrt(line[0] * line[0] + line[1] * line[1]);
return fabs((x.x - line[2]) * line[1] - (x.y - line[3]) * line[0]) / det;
}
double CFitLineRANSAC::VerificationLineModel(const cv::Vec4f &estimated_model, const double &distance_threshold, const vector<cv::Point2f> &src, vector<cv::Point2f> &dst)
{
double cost = 0.0;
for(size_t i = 0; i < src.size(); i++)
{
if (ComputeDistancePoint(estimated_model, src[i]) < distance_threshold)
{
cost += 1.0;
dst.push_back(src[i]);
}
}
return cost;
}
'머신 비전 > 머신 비전 알고리즘 테크닉 CPP' 카테고리의 다른 글
머신 비전 알고리즘 - OpenCV - 이미지처리31 (0) | 2021.08.20 |
---|---|
머신 비전 알고리즘 - OpenCV - 이미지처리30 (0) | 2021.08.15 |
머신 비전 알고리즘 - OpenCV - 이미지처리28 (0) | 2021.08.10 |
머신 비전 알고리즘 - OpenCV - 이미지처리27 (0) | 2021.08.07 |
머신 비전 알고리즘 - OpenCV - 이미지처리26 (0) | 2021.08.01 |