OpenCV图像纹理
- 软件开发
- 2025-08-12 14:18:01

LBP描述
LBP(Local Binary Pattern,局部二值模式)是一种用来描述图像局部纹理特征的算子;它具有旋转不变性和灰度不变性等显著的优点。它是首先由T. Ojala, M.Pietikäinen, 和D. Harwood 在1994年提出,用于纹理特征提取。而且,提取的特征是图像的局部的纹理特征
计算过程原始的LBP算子定义为在3\*3的窗口内,以窗口中心像素为阈值,将相邻的8个像素的灰度值与其进行比较,若周围像素值大于中心像素值,则该像素点的位置被标记为1,否则为0。这样,3\*3邻域内的8个点经比较可产生8位二进制数(通常转换为十进制数即LBP码,共256种),即得到该窗口中心像素点的LBP值,并用这个值来反映该区域的纹理信息。数学表达式方式如下图所示
上述表述可能会比较抽象,接下来我们举一个例子表述 一下:
代码实现
class LBP { public: LBP(string url = "mm.jpg") :img(imread(url, IMREAD_GRAYSCALE)) { result["img"] = img; } void GetLBP() { result["LBP"] = Mat::zeros(img.rows - 2, img.cols - 2, CV_8UC1); for (int i = 1; i < img.rows - 1; i++) { for (int j = 1; j < img.cols - 1; j++) { uchar temp = img.at<uchar>(i, j); uchar color = 0; color |= (img.at<uchar>(i - 1, j - 1) > temp) << 7; color |= (img.at<uchar>(i - 1, j) > temp) << 6; color |= (img.at<uchar>(i - 1, j + 1) > temp) << 5; color |= (img.at<uchar>(i, j + 1) > temp) << 4; color |= (img.at<uchar>(i+1, j + 1) > temp) << 3; color |= (img.at<uchar>(i+1, j) > temp) << 2; color |= (img.at<uchar>(i+1, j - 1) > temp) << 1; color |= (img.at<uchar>(i, j - 1) > temp) << 0; result["LBP"].at<uchar>(i - 1, j - 1) = color; } } } void Show() { for (auto v : result) { imshow(v.first, v.second); } waitKey(0); } protected: map<string, Mat> result; Mat img; };SIFT特征检测
尺度不变特征转换(Scale-invariant feature transform或SIFT)是一种电脑视觉的算法用来侦测与描述影像中的局部性特征,它在空间尺度中寻找极值点,并提取出其位置、尺度、旋转不变量,此算法由 David Lowe在1999年所发表,2004年完善总结。 其应用范围包含物体辨识、机器人地图感知与导航、影像缝合、3D模型建立、手势辨识、影像追踪和动作比对。
SIFT算法是为了解决图片的匹配问题,想要从图像中提取一种对图像的大小和旋转变化保持鲁棒的特征,从而实现匹配。这一算法的灵感也十分的直观:人眼观测两张图片是否匹配时会注意到其中的典型区域(特征点部分),如果我们能够实现这一特征点区域提取过程,再对所提取到的区域进行描述就可以实现特征匹配了。
SIFT算法大致流程 高斯金字塔 人看物体时近大远小,可以对图片下采样实现远处模糊,可以对图像高斯平滑实现 高斯差分金字塔特征提取 获取了不同尺度的图片获取高频区域(边缘检测的算法使用差分滤波器如拉普拉斯滤波器、sobel滤波器)
特征点处理 阈值化操作(去噪)非极大值抑制二阶泰勒修正低对比度去除边缘效应去除
描述特征点 确定特征点区域方向特征点区域描述子
API介绍
static Ptr<SIFT> create(int nfeatures = 0, int nOctaveLayers = 3,double contrastThreshold = 0.04, double edgeThreshold = 10,double sigma = 1.6); /******************************************************************* * nfeatures: 保留的最佳特性的数量 * cornOctaveLayersners: 高斯金字塔最小层级数 * contrastThreshold: 对比度阈值用于过滤区域中的弱特征 * edgeThreshold: 用于过滤掉类似边缘特征的阈值 * sigma: 高斯输入层级 *********************************************************************/
virtual void detect( InputArray image,std::vector<KeyPoint>& keypoints,InputArray mask=noArray()); /******************************************************************* * image: 输入图 * keypoints: 角点信息 * mask: 计算亚像素角点区域大小 *********************************************************************/
void drawKeypoints( InputArray image, const std::vector<KeyPoint>& keypoints, InputOutputArray outImage,const Scalar& color=Scalar::all(-1), DrawMatchesFlags flags=DrawMatchesFlags::DEFAULT ); /******************************************************************* * image: 输入图 * keypoints: 角点信息 * outImage: 输出图 * color: 颜色 * flags: 绘制标记 *********************************************************************/
完整代码 #include <iostream> #include <map> #include <new> #include <opencv2/opencv.hpp> using namespace std; using namespace cv; class SIFTFeature { public: SIFTFeature() :img(imread("mm.jpg")) { result["img"] = img; } void TestSIFT() { Ptr<SIFT> sift = SIFT::create(); sift->detect(img, point); drawKeypoints(img, point, result["SIFT"], Scalar(255, 0, 255)); } void Show() { for (auto& v : result) { imshow(v.first, v.second); } waitKey(0); } protected: Mat img; vector<KeyPoint> point; map<string, Mat> result; }; int main() { unique_ptr<SIFTFeature> p(new SIFTFeature); p->TestSIFT(); p->Show(); return 0; }效果图:
OpenCV图像纹理由讯客互联软件开发栏目发布,感谢您对讯客互联的认可,以及对我们原创作品以及文章的青睐,非常欢迎各位朋友分享到个人网站或者朋友圈,但转载请说明文章出处“OpenCV图像纹理”