資源簡介
Frankot and Chellappa算法C++代碼實現(xiàn)。重建面型的梯度場與測得梯度場的總體誤差最小化,通過傅里葉變換將一系列不可積的梯度場映射到頻域中一系列可積的基本函數(shù)的組合
代碼片段和文件信息
//傅里葉變換
void?Fouriertransform(cv::Mat&?src?cv::Mat&?complexImg)
{
int?M?=?cv::getOptimalDFTSize(src.rows);
int?N?=?cv::getOptimalDFTSize(src.cols);
cv::Mat?padded;
cv::copyMakeBorder(src?padded?0?M?-?src.rows?0?N?-?src.cols?cv::BORDER_CONSTANT?cv::Scalar::all(0));
cv::Mat?planes[]?=?{?cv::Mat_(padded)?cv::Mat::zeros(padded.size()?CV_32F)?};
cv::merge(planes?2?complexImg);
dft(complexImg?complexImg);
}
void?dftshift(cv::Mat&?ds)
{
int?cx?=?ds.cols?/?2;//圖像的中心點x?坐標
int?cy?=?ds.rows?/?2;//圖像的中心點y?坐標
cv::Mat?q0?=?ds(cv::Rect(0?0?cx?cy));//左上
cv::Mat?q1?=?ds(cv::Rect(cx?0?cx?cy));//右上
cv::Mat?q2?=?ds(cv::Rect(0?cy?cx?cy));//左下
cv::Mat?q3?=?ds(cv::Rect(cx?cy?cx?cy));//右下
cv::Mat?tmp;
q0.copyTo(tmp);
q3.copyTo(q0);
tmp.copyTo(q3);
q1.copyTo(tmp);
q2.copyTo(q1);
tmp.copyTo(q2);
}
//傅里葉逆變換
void?InvFouriertransform(cv::Mat&?src?cv::Mat&?dst)
{
cv::idft(src?dst/*?cv::DFT_SCALE?|?cv::DFT_REAL_OUTPUT*/);
dst.convertTo(dst?CV_32F);
}
//保存數(shù)據(jù)點
void?SavePointData(cv::Mat&?srcstring&?filename)
{
printf(“保存數(shù)據(jù)中!\n“);
int?rows?=?src.rows;
int?cols?=?src.cols;
string?filepath?=?“D:\\specular_surface\\calib\\Test\\“;
filepath?=?filepath?+?filename;
double?time1?=?cv::getTickCount();
std::ofstream?outfile;
outfile.open(filepath);
for?(int?i?=?0;?i? {
float?*?src_ptr?=?src.ptr(i);
for?(int?j?=?0;?j? {
outfile?< }
}
outfile.close();
printf(“保存文件時間:%f\n“?(cv::getTickCount()?-?time1)?/?cv::getTickFrequency());
}
//求取整幅圖像絕對值得最大和最小值
void?MinMaxAbValue(cv::Mat&?src?double?&?maxv?double&?minv)
{
if?(src.type()?!=?CV_32FC1)
{
src.convertTo(src?CV_32FC1);
}
int?rows?=?src.rows;
int?cols?=?src.cols;
maxv?=?0;
minv?=?cv::NORM_INF;
for?(int?i?=?0;?i? {
float?*?ptr?=?src.ptr(i);
for?(int?j?=?0;?j? {
if?(abs(ptr[j])?>?maxv)
{
maxv?=?abs(ptr[j]);
}
if?(abs(ptr[j])? {
minv?=?abs(ptr[j]);
}
}
}
}
//乘以虛數(shù)j
void?MultiplyJ(cv::Mat&?src?cv::Mat&?dst)
{
cv::Mat?planes[2];
cv::split(src?planes);
cv::Mat?real?image;
real?=?planes[0];
image?=?planes[1];
cv::Mat?dd?=?cv::Mat::zeros(src.size()?CV_32FC1);
cv::subtract(dd?real?real);
cv::Mat?temp?=?image;
planes[1]?=?real;
planes[0]?=?image;
cv::merge(planes?2?dst);
}
//計算梯度
void?CalcGradient(const?cv::Mat1f&?matPhasetan?cv::Mat&?matGradient_X?cv::Mat&?matGradient_Y)
{
matGradient_X?=?cv::Mat1f(matPhasetan.rows?matPhasetan.cols);
matGradient_Y?=?cv::Mat1f(matPhasetan.rows?matPhasetan.cols);
for?(int?i?=?0;?i? {
for?(int?j?=?0;?j?
評論
共有 條評論