C++ opencv圖像處理實(shí)現(xiàn)圖片幾何變換示例
簡介
圖像的幾何變換不改變圖像的像素值,而是改變像素所在的幾何位置,從變換的性質(zhì)來分,圖像的幾何變換有圖像的位置變換(平移,鏡像,旋轉(zhuǎn))、圖像的形狀變換(放大,縮小,錯(cuò)切)等基本變換,以及圖像的復(fù)合變換等,
一、圖像平移
圖像平移是將一幅圖像中所有的點(diǎn)都按照指定的平移量在水平,垂直方向移動(dòng),平移后的圖像與原圖像相同,平移后的圖像上的每一個(gè)點(diǎn)都可以在原圖像中找到對(duì)應(yīng)的點(diǎn)。圖像是由像素組成,假設(shè)原來的像素坐標(biāo)為(x0,y0),經(jīng)過平移量(△x,△y)坐標(biāo)變?yōu)椋▁1,y1)
用數(shù)學(xué)可以表示:x1=x0+△x,y1=y0+△xy
平移變換分為兩種,一種是圖像大小改變,這樣最后的原圖像會(huì)有一部分不在圖像中,另一種是圖像大小改變,這樣可以保全原圖像的內(nèi)容
1.圖像平移代碼 (不改變圖像大?。?/h3>
#include<iostream>
#include<opencv.hpp>
using namespace std;
using namespace cv;
int main()
{
Mat img1;
img1 = imread("貓1.jpg");
imshow("原圖", img1);
int r = img1.rows;
int c = img1.cols;
int x0 = 100;
int y0 = 100;
Mat img2(img1.size(), img1.type());
for (int i = 0; i < r; i++)
{
for (int j = 0; j < c; j++)
{
int x = j - x0;
int y = i - y0;
if (x >= 0 && y >= 0 && x < c&&y < r)
{
img2.at<Vec3b>(i, j) = img1.ptr<Vec3b>(y)[x];
}
}
}
imshow("不改變圖像大小", img2);
waitKey(0);
}
#include<iostream>
#include<opencv.hpp>
using namespace std;
using namespace cv;
int main()
{
Mat img1;
img1 = imread("貓1.jpg");
imshow("原圖", img1);
int r = img1.rows;
int c = img1.cols;
int x0 = 100;
int y0 = 100;
Mat img2(img1.size(), img1.type());
for (int i = 0; i < r; i++)
{
for (int j = 0; j < c; j++)
{
int x = j - x0;
int y = i - y0;
if (x >= 0 && y >= 0 && x < c&&y < r)
{
img2.at<Vec3b>(i, j) = img1.ptr<Vec3b>(y)[x];
}
}
}
imshow("不改變圖像大小", img2);
waitKey(0);
}
效果如下:

2.圖像平移代碼 (改變圖像大?。?/h3>
代碼如下(示例):
int main()
{
Mat img1;
img1 = imread("貓1.jpg");
imshow("原圖", img1);
int x0 = 100;
int y0 = 100;
int r = img1.rows + y0;
int c = img1.cols + x0;
Mat img2(r,c, img1.type());
for (int i = 0; i < r; i++)
{
for (int j = 0; j < c; j++)
{
int x = j - x0;
int y = i - y0;
if (x >= 0 && y >= 0 && x < c&&y < r)
{
img2.at<Vec3b>(i, j) = img1.ptr<Vec3b>(y)[x];
}
}
}
imshow("改變圖像大小", img2);
waitKey(0);
}
效果如下:

二、圖像旋轉(zhuǎn)
圖像旋轉(zhuǎn)是數(shù)字圖像處理的一個(gè)非常重要的環(huán)節(jié),是圖像的幾何變換的手法之一。一般圖像的旋轉(zhuǎn)是圖像的位置變換,但旋轉(zhuǎn)后,圖像的大小一般會(huì)改變。在圖像旋轉(zhuǎn)變換中,既可以把轉(zhuǎn)出顯示區(qū)域的圖像截去,也可以擴(kuò)大圖像范圍以顯示所用的圖像。
1.圖像旋轉(zhuǎn)函數(shù)
opencv提供的getRotationMatrix2D函數(shù)來實(shí)現(xiàn)圖像旋轉(zhuǎn),用來計(jì)算出旋轉(zhuǎn)矩陣。
Mat getRotationMatrix2D(Point2f center, double angle, double scale) center 旋轉(zhuǎn)中心點(diǎn) angle 旋轉(zhuǎn)的角度 scale 圖像縮放因子
2.仿射變換函數(shù)
計(jì)算出旋轉(zhuǎn)矩陣后,還需要把旋轉(zhuǎn)應(yīng)用到仿射變換的輸出,仿射變換函數(shù)是warpAffine
void warpAffine(InputArray src, OutputArray dst, InputArray M, Size dsize, int flags = INTER_LINEAR, int borderMode = BORDER_CONSTANT, const Scalar& borderValue = Scalar()); src 輸入 dst 輸出 M 變換矩陣 Size 尺寸 flags 插值算法標(biāo)識(shí)符 borderMode 邊界像素模式 borderValue 邊界取值
3.代碼
int main()
{
Mat img1;
img1 = imread("貓1.jpg");
imshow("原圖", img1);
Point center(img1.cols / 2, img1.rows / 2);
Mat m = getRotationMatrix2D(center, 30, 0.5);
Mat img2;
warpAffine(img1, img2, m, img1.size());
imshow("旋轉(zhuǎn)", img2);
waitKey(0);
}
效果如下:

三、圖像縮放
圖像比例縮放是值將給定的圖像在x軸方向按比例縮放fx倍,在y軸方向按比例縮放fy倍
1.圖像縮放函數(shù)
void resize(InputArray src, OutputArray dst, Size dsize, double fx = 0, double fy = 0, int interpolation = INTER_LINEAR); src 輸入 dst 輸出 dsize 尺寸 fx 在x軸縮放比例 fy 在y軸縮放比例 interpolation 插值方式
2.圖像縮小代碼
int main()
{
Mat img1;
img1 = imread("貓1.jpg");
imshow("原圖", img1);
Mat img2;
resize(img1, img2, Size(img1.cols / 2, img1.rows / 2));
imshow("縮小", img2);
waitKey(0);
}
效果如下:

3.圖像放大代碼
int main()
{
Mat img1;
img1 = imread("貓1.jpg");
imshow("原圖", img1);
Mat img2;
resize(img1, img2, Size(img1.cols * 2, img1.rows * 2));
imshow("放大", img2);
waitKey(0);
}
效果如下:

總結(jié)
本文簡單介紹了圖像平移,旋轉(zhuǎn),縮放,這是最基本的調(diào)用函數(shù)解決,其中還有運(yùn)用數(shù)學(xué)公式解決,這里沒有介紹,有興趣的可以去了解了解,更多關(guān)于C++ opencv幾何變換的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
適合初學(xué)者的C語言數(shù)據(jù)類型的講解
在 C 語言中,數(shù)據(jù)類型指的是用于聲明不同類型的變量或函數(shù)的一個(gè)廣泛的系統(tǒng)。變量的類型決定了變量存儲(chǔ)占用的空間,以及如何解釋存儲(chǔ)的位模式。2022-04-04
c++11 chrono全面解析(最高可達(dá)納秒級(jí)別的精度)
chrono是c++ 11中的時(shí)間庫,本文就來詳細(xì)的介紹一下chrono庫的具體使用,關(guān)鍵是理解里面時(shí)間段(Durations)、時(shí)間點(diǎn)(Time points)的概念,感興趣的可以了解一下2021-11-11
C++實(shí)現(xiàn)圖形界面時(shí)鐘表盤代碼
這篇文章主要介紹了C++實(shí)現(xiàn)圖形界面時(shí)鐘表盤代碼,涉及坐標(biāo)函數(shù)的應(yīng)用及圖形界面程序設(shè)計(jì),需要的朋友可以參考下2014-10-10
C++ Boost實(shí)現(xiàn)數(shù)字與字符串轉(zhuǎn)化詳解
Boost是為C++語言標(biāo)準(zhǔn)庫提供擴(kuò)展的一些C++程序庫的總稱。Boost庫是一個(gè)可移植、提供源代碼的C++庫,作為標(biāo)準(zhǔn)庫的后備,是C++標(biāo)準(zhǔn)化進(jìn)程的開發(fā)引擎之一,是為C++語言標(biāo)準(zhǔn)庫提供擴(kuò)展的一些C++程序庫的總稱2022-11-11
C++中的動(dòng)態(tài)規(guī)劃子序列問題分析探討
可能有些讀者有接觸過動(dòng)態(tài)規(guī)劃,可能也有一些讀者以前完全不知道動(dòng)態(tài)規(guī)劃這個(gè)東西,別擔(dān)心,我這篇文章會(huì)為讀者做一個(gè)入門,好讓讀者掌握這個(gè)重要的知識(shí)點(diǎn)2023-03-03

