日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

5.8 直方图统计

發布時間:2025/3/15 编程问答 34 豆豆
生活随笔 收集整理的這篇文章主要介紹了 5.8 直方图统计 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.


5.8.1 灰度圖像直方圖

直方圖統計是圖像處理中的一個非常重要的操作。VTK中實現直方圖統計功能的filter是vtkImageAccumulate。其將每個組分的數值范圍劃分為離散的間隔,然后統計每個灰度間隔上的像素數目。vtkImageAccumulate輸入和輸出都是vtkImageData類型,因此直方圖也可以看做是一幅圖像;對于輸入圖像的像素數據類型可以是任意的,但是最大支持3個組分像素類型,而輸出圖像的像素數據類型為int型。一個灰度圖像的直方圖為一個一維圖像。首先來看一下怎么計算灰度圖像直方圖。

?

?? 1:?????vtkSmartPointer<vtkJPEGReader> reader =

?? 2:?????????vtkSmartPointer<vtkJPEGReader>::New();

?? 3:?????reader->SetFileName ( " lena2.jpg" );

?? 4:?????reader->Update();

?? 5:??

?? 6:?????int bins = 16;

?? 7:??

?? 8:?????vtkSmartPointer<vtkImageAccumulate> histogram =

?? 9:?????????vtkSmartPointer<vtkImageAccumulate>::New();

? 10:?????histogram->SetInput(reader->GetOutput());

? 11:?????histogram->SetComponentExtent(0, bins-1, 0, 0, 0, 0);

? 12:?????histogram->SetComponentOrigin(0, 0, 0);

? 13:?????histogram->SetComponentSpacing(256/bins, 0, 0);

? 14:?????histogram->Update();

? 15:??

? 16:?????vtkSmartPointer<vtkIntArray> frequencies =

? 17:?????????vtkSmartPointer<vtkIntArray>::New();

? 18:??

? 19:?????frequencies->SetNumberOfComponents(1);

? 20:?????frequencies->SetNumberOfTuples(bins);

? 21:?????int* output = static_cast<int*>(histogram->GetOutput()->GetScalarPointer());

? 22:??

? 23:?????for(int j = 0; j < bins; ++j)

? 24:?????{

? 25:?????????frequencies->SetTuple1(j, *output++);

? 26:?????}

? 27:??

? 28:?????vtkSmartPointer<vtkDataObject> dataObject =

? 29:?????????vtkSmartPointer<vtkDataObject>::New();

? 30:?????dataObject->GetFieldData()->AddArray( frequencies );

? 31:??

? 32:?????vtkSmartPointer<vtkBarChartActor> barChart =

? 33:?????????vtkSmartPointer<vtkBarChartActor>::New();

? 34:??

? 35:?????barChart->SetInput(dataObject);

? 36:?????barChart->SetTitle("Histogram");

? 37:?????barChart->GetPositionCoordinate()->SetValue(0.05,0.05,0.0);

? 38:?????barChart->GetPosition2Coordinate()->SetValue(0.95,0.95,0.0);

? 39:?????barChart->GetProperty()->SetColor(1,1,1);

? 40:??

? 41:?????barChart->GetLegendActor()->SetNumberOfEntries(

? 42:?????????????dataObject->GetFieldData()->GetArray(0)->GetNumberOfTuples());

? 43:?????barChart->LegendVisibilityOff();

? 44:?????barChart->LabelVisibilityOff();

? 45:??

? 46:?????double red[3] = {1, 0, 0 };

? 47:?????for(int i = 0; i < bins; ++i)

? 48:?????{

? 49:?????????barChart->SetBarColor(i, red );

? 50:?????}

? 51:??

? 52:?????vtkSmartPointer<vtkRenderer> renderer =

? 53:?????????vtkSmartPointer<vtkRenderer>::New();

? 54:?????renderer->AddActor(barChart);

? 55:??

? 56:?????vtkSmartPointer<vtkRenderWindow> renderWindow =

? 57:?????????vtkSmartPointer<vtkRenderWindow>::New();

? 58:?????renderWindow->AddRenderer(renderer);

? 59:?????renderWindow->SetSize(640, 480);

? 60:??

? 61:?????vtkSmartPointer<vtkRenderWindowInteractor> interactor =

? 62:?????????vtkSmartPointer<vtkRenderWindowInteractor>::New();

? 63:?????interactor->SetRenderWindow(renderWindow);

? 64:?????interactor->Initialize();

? 65:?????interactor->Start();

?

下面來分析一下代碼。首先是讀入一副灰度圖像,一般的灰度圖像的灰度范圍為0-255。定義了一個變量bins = 16,表示要圖像灰度范圍上的間隔數目,也可以理解為直方圖一維數組的維數。然后定義vtkImageAccumulate對象,并設置輸入數據為我們讀入的圖像數據,接著調用了三個函數:

SetComponentExtent(0,bins-1, 0, 0, 0, 0),該函數設置要計算每個組分的直方圖的最小和最大值。vtkImageAccumulate最大支持像素值為三個組分(如RGB圖像)的直方圖,支持共有六個參數。分別表示每個組分的直方圖最小和最大值。該例中由于計算的是灰度圖像直方圖,只有一個組分,因此第二個和第三個組分都設置為0;而第一組分直方圖維數為bins = 16,那么其最小和最大范圍為0和bins-1。

SetComponentOrigin(0,0, 0),該函數設置的是統計每個組分直方圖時的起始灰度值,這里設置為0,表示灰度從0開始統計直方圖。同樣,vtkImageAccumulate最大支持像素值為三個組分,這里也要設置三個參數。如果圖像的灰度范圍為[1000, 2000],那么計算直方圖時,其起始灰度應該設置為1000。

SetComponentSpacing(16,0, 0),設置直方圖每個間隔代表的灰度范圍,例如當一個圖像灰度范圍為[1000, 2000],統計直方圖的間隔數bins為100時,那么對應的space應該設置為SetComponentSpacing(100, 0, 0)。

參數設置完畢后執行Update()即可計算直方圖。前面已經提到過,vtkImageAccumulate的輸出結果也是一個vtkImageData類型,這樣就可以方便的訪問圖像的每個數據。圖像像素訪問前面已經介紹過,這里就不在重述。需要注意的是輸出直方圖圖像的數據類型為int。

這里再順便簡單的介紹一下直方圖的顯示。雖然vtkImageAccumulate的輸出類型為vtkImageData但是并不能直接按照圖像的方式進行顯示。VTK中定義了vtkBarChartActor用來顯示條形圖,因此可以利用其來顯示直方圖。但是該類接收的數據類型為vtkDataObject類型,因此需要先將直方圖數據進行轉換。首先將直方圖數組存儲到vtkIntArray數組frequencies中,通過函數vtkDataObject函數GetFieldData()->AddArray(frequencies)將其添加到vtkDataObject對象中。vtkBarChartActor對象接收vtkDataObject對象作為輸入,另外還需要設置圖表的名字,顏色等,需要注意兩個函數:

barChart->GetPositionCoordinate()->SetValue(0.05,0.05,0.0);

barChart->GetPosition2Coordinate()->SetValue(0.95,0.95,0.0);

這里設置的是窗口中顯示圖表的所在矩形的左下角點和右上角點坐標,VTK的坐標系原點位于左下角點,設置時需要格外注意。設置完畢后,即可定義相應的vtkRenderer,vtkRenderWindow和vtkRenderWindowInteractor對象顯示圖像直方圖。本例的顯示效果如下:

?

圖5.20 VTK直方圖顯示

?

5.8.2 彩色圖像直方圖

彩色圖像由于內部有三個通道,不能直接計算直方圖,需要提取RGB三個通道數據,分別計算直方圖。每個通道計算直方圖的方法與灰度圖像直方圖計算方法一致。下面給出相關代碼:

1:????? vtkSmartPointer<vtkBMPReader>reader =

?? 2:?????????vtkSmartPointer<vtkBMPReader>::New();

?? 3:?????reader->SetFileName ( "lena.bmp" );

?? 4:?????reader->Update();

?? 5:??

?? 6:?????int numComponents =reader->GetOutput()->GetNumberOfScalarComponents();

?? 7:??

?? 8:?????vtkSmartPointer<vtkXYPlotActor> plot =

?? 9:?????????vtkSmartPointer<vtkXYPlotActor>::New();

? 10:?????plot->ExchangeAxesOff();

? 11:?????plot->SetLabelFormat( "%g" );

? 12:?????plot->SetXTitle( "Value" );

? 13:?????plot->SetYTitle( "Frequency" );

? 14:?????plot->SetXValuesToValue();

? 15:??

? 16:?????double colors[3][3] = {

? 17:?????????{ 1, 0, 0 },

? 18:?????????{ 0, 1, 0 },

? 19:?????????{ 0, 0, 1 }

? 20:?? ???};

? 21:??

? 22:?????const char* labels[3] = { "Red", "Green","Blue" };

? 23:??

? 24:?????int xmax = 0;

? 25:?????int ymax = 0;

? 26:??

? 27:?????for( int i = 0; i < numComponents; ++i )

? 28:?????{

? 29:?????????vtkSmartPointer<vtkImageExtractComponents> extract =

? 30:?????????????vtkSmartPointer<vtkImageExtractComponents>::New();

? 31:?????????extract->SetInputConnection( reader->GetOutputPort() );

? 32:?????????extract->SetComponents( i );

? 33:?????????extract->Update();

? 34:??

? 35:?????????double range[2];

? 36:?????????extract->GetOutput()->GetScalarRange( range );

? 37:?????????int extent =static_cast<int>(range[1])-static_cast<int>(range[0])-1;

? 38:??

? 39:?????????vtkSmartPointer<vtkImageAccumulate> histogram =

? 40:?????????????vtkSmartPointer<vtkImageAccumulate>::New();

? 41:?????????histogram->SetInputConnection( extract->GetOutputPort() );

? 42:?????????histogram->SetComponentExtent( 0,extent, 0,0, 0,0);

? 43:?????????histogram->SetComponentOrigin( range[0],0,0 );

? 44:?????????histogram->SetComponentSpacing( 1,0,0 );

? 45:?????????histogram->SetIgnoreZero( 1 );

? 46:?????????histogram->Update();

? 47:??

? 48:?????????if( range[1] > xmax )

? 49:?????????{

? 50:????????????? xmax = range[1];

? 51:? ????????}

? 52:?????????if( histogram->GetOutput()->GetScalarRange()[1] > ymax )

? 53:?????????{

? 54:????????????? ymax =histogram->GetOutput()->GetScalarRange()[1];

? 55:?????????}

? 56:??

? 57:?????????plot->AddInput( histogram->GetOutput() );

? 58:?????????plot->SetPlotColor(i,colors[i]);

? 59:?????????plot->SetPlotLabel(i,labels[i]);

? 60:?????????plot->LegendOn();

? 61:?????}

? 62:??

? 63:?????plot->SetXRange( 0, xmax);

? 64:?????plot->SetYRange( 0, ymax);

? 65:??

? 66:?????vtkSmartPointer<vtkRenderer> renderer =

? 67:?????????vtkSmartPointer<vtkRenderer>::New();

? 68:?????renderer->AddActor(plot);

? 69:??

? 70:?????vtkSmartPointer<vtkRenderWindow> renderWindow =

? 71:?????????vtkSmartPointer<vtkRenderWindow>::New();

? 72:?????renderWindow->AddRenderer( renderer );

? 73:?????renderWindow->SetSize(640, 480);

? 74:??

? 75:?????vtkSmartPointer<vtkRenderWindowInteractor> interactor =

? 76:?????????vtkSmartPointer<vtkRenderWindowInteractor>::New();

? 77:?????interactor->SetRenderWindow( renderWindow );

? 78:??

? 79:?????interactor->Initialize();

? 80:?????interactor->Start();

?

上面代碼說明了怎樣計算彩色圖像直方圖。計算直方圖的主要代碼段是27-61行。由于彩色圖像不能直接計算直方圖,因此需要先通過vtkImageExtractComponents來提取每個通道圖像,然后再利用vtkImageAccumulate統計直方圖。在本例中計算直方圖的間隔取(1, 0, 0),即每個灰度計算統計一個頻率,而且灰度起點為圖像的最小灰度值,這樣間隔的個數即為:最大灰度值減去最小灰度值,再減1,如第37行代碼。同時,設置了SetIgnoreZero()為1,即在統計直方圖時,像素值為0的像素不進行統計。

在灰度圖像直方圖實例中,我們使用的是vtkBarChartActor柱狀圖來顯示直方圖,在本例中則使用vtkXYPlotActor曲線來表示直方圖,這里做一簡單介紹。vtkXYPlotActor類可以用來顯示二維曲線,它可以接收多個輸入數據,如本例中我們輸入了三條曲線,分別是圖像紅色分量直方圖區域,綠色分量直方圖曲線和藍色分量直方圖曲線。SetXRange()和SetYRange()用來設置X軸和Y軸的數據范圍,另外還可以設置X軸和Y軸的名字,曲線的標題等屬性,詳細可以查閱vtkXYPlotActor類的文檔。vtkXYPlotActor類是一個vtkActor2D的子類,因此定義相應的vtkRenderer,vtkRenderWindow和vtkRenderWindowInteractor對象建立可視化管道來顯示圖像直方圖曲線。本例的顯示效果如下:其中,紅色曲線代碼紅色分量的直方圖,綠色代表綠色分量的直方圖曲線,藍色代碼藍色分量的直方圖曲線。

?

圖5.21 彩色圖像直方圖

5.9 圖像重采樣

圖像重采樣是指對采樣后形成的由離散數據組成的數字圖像按所需的像元位置或像元問距重新采樣,以構成幾何變換后的新圖像。重采樣過程本質上是圖像恢復過程,它用輸入的離散數字圖像重建代表原始圖像二維連續函數,再按新的像元間距和像元位置進行采樣。其數學過程是根據重建的連續函數(曲面),用周圍若干像元點的值估計或內插出新采樣點的值。圖像重采樣在圖像處理中應用非常廣泛,如SIFT特征提取。

圖像重采樣后圖像的維數會發生改變。當重采樣圖像小于原圖像維數時,稱為降采樣;當重采樣圖像維數大于原圖像時,稱為升采樣。VTK中可以方便的對圖像進行重采樣。vtkImageShrink3D類實現圖像降采樣。降采樣需要設置每個方向的采樣率,降采樣率越大,圖像越模糊。升采樣的原理與降采樣原理一致,只是增加采樣點數來增加圖像的維數。VTK中vtkImageMagnify來實現圖像的升采樣。下面看一個實例。

?

1:????? vtkSmartPointer<vtkBMPReader>reader =

??2:?????????vtkSmartPointer<vtkBMPReader>::New();

??3:????? reader->SetFileName (" lena.bmp" );

??4:????? reader->Update();

??5:??

??6:?????vtkSmartPointer<vtkImageShrink3D> shrinkFilter =

??7:?????????vtkSmartPointer<vtkImageShrink3D>::New();

??8:?????shrinkFilter->SetInputConnection(reader->GetOutputPort());

??9:?????shrinkFilter->SetShrinkFactors(20,20,1);

?10:?????shrinkFilter->Update();

?11:??

?12:?????vtkSmartPointer<vtkImageMagnify> magnifyFilter =

?13:????????? vtkSmartPointer<vtkImageMagnify>::New();

?14:?????magnifyFilter->SetInputConnection(reader->GetOutputPort());

?15:?????magnifyFilter->SetMagnificationFactors(10,10,1);

?16:?????magnifyFilter->Update();

?17:??

?18:????? int originalDims[3];

?19:????? reader->GetOutput()->GetDimensions(originalDims);

?20:??

?21:????? double originalSpace[3];

?22:?????reader->GetOutput()->GetSpacing(originalSpace);

?23:??

?24:????? int shrinkDims[3];

?25:?????shrinkFilter->GetOutput()->GetDimensions(shrinkDims);

?26:??

?27:????? double shrinkSpace[3];

?28:?????shrinkFilter->GetOutput()->GetSpacing(shrinkSpace);

?29:??

?30:????? int magnifyDims[3];

?31:?????magnifyFilter->GetOutput()->GetDimensions(magnifyDims);

?32:??

?33:????? double magnifySpace[3];

?34:?????magnifyFilter->GetOutput()->GetSpacing(magnifySpace);

?35:??

?36:????? std::cout<<"原圖圖像維數????? :"<<originalDims[0]<< " "<<originalDims[1]<<""<<originalDims[2]<<std::endl;

?37:????? std::cout<<"原圖圖像像素間隔? :"<<originalSpace[0]<< " "<<originalSpace[1]<<""<<originalSpace[2]<<std::endl;

?38:????? std::cout<<"降采樣圖像維數??? :"<<shrinkDims[0]<< " "<<shrinkDims[1]<<""<<shrinkDims[2]<<std::endl;

?39:????? std::cout<<"降采樣圖像像素間隔:"<<shrinkSpace[0]<< " "<<shrinkSpace[1]<<""<<shrinkSpace[2]<<std::endl;

?40:????? std::cout<<"升采樣圖像維數??? :"<<magnifyDims[0]<< " "<<magnifyDims[1]<<""<<magnifyDims[2]<<std::endl;

?41:????? std::cout<<"升采樣圖像像素間隔:"<<magnifySpace[0]<< " "<<magnifySpace[1]<<""<<magnifySpace[2]<<std::endl;

?

vtkImageShrink3D使用時通過SetShrinkFactors()設置X、Y和Z方向的采樣率,參數為三個int類型數據。vtkImageMagnify的使用也是類似,通過SetMagnificationFactors設置相應的放大采樣率。上面例子中分別對原圖像維數縮小原來的1/20和放大為原來的10倍,執行結果如下:

?

圖5.22 圖像重采樣

?

從圖中可以看成,重采樣圖像已經變得十分模糊了。而升采樣圖像則變化不大。程序中輸出了原圖和重采樣圖像的維數和像素間隔,從輸出來看,原圖像的維數為512x512,縮小20倍后,圖像維數變為25x25。需要注意的是,原圖的像素間隔為(1,1,1),而重采樣后像素間隔變為(20, 20, 1),這是因為采樣是在世界坐標系下進行的,當采樣圖像的維數減小時,采樣的像素間隔也相應的變大,這樣保持圖像的區域不會發生改變。同樣的道理,當升采樣后圖像的維數變為原來的10倍,而像素間隔變為原來的十分之一。

另外,圖像的重采樣類有:vtkImageResample。


==========歡迎轉載,轉載時請保留該聲明信息==========

版權歸@東靈工作室所有,更多信息請訪問東靈工作室


教程系列導航:http://blog.csdn.net/www_doling_net/article/details/8763686

================================================

總結

以上是生活随笔為你收集整理的5.8 直方图统计的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 91久久久久久久久久 | 99re6在线观看 | 一级片免费在线 | 全国最大色 | 欧美操老女人 | 性感美女被草 | 欧美精品一二三区 | 人妻体内射精一区二区 | 最新日韩在线 | 神马久久久久久久久 | 天天草天天爽 | 美女100%视频免费观看 | 日日夜夜精品免费视频 | 强开小受嫩苞第一次免费视频 | 亚洲人成无码网站久久99热国产 | 亚洲国产成人一区二区精品区 | 涩涩网站视频 | 精品五月天 | 久久思 | 好吊色视频988gao在线观看 | 在线观看日本中文字幕 | av东方在线 | 97超碰人人模人人人爽人人爱 | 亚洲裸体视频 | 污视频网站免费看 | 樱花视频在线免费观看 | 97人人爽| 男生插女生视频在线观看 | 国产午夜视频在线观看 | 天天天天天天操 | 黄色一级大片在线观看 | 国产免费a| 久久只有这里有精品 | av片子在线观看 | 亚洲一区二区黄色 | 日日爱av| 先锋av资源在线 | 日韩va在线观看 | 欧美成人91 | 日韩精品高清在线 | 色哥网 | 亚洲一区二区三区三州 | 在线一二区 | 怡红院男人天堂 | 97超碰人人澡人人爱学生 | 午夜精品久久99蜜桃的功能介绍 | 1级片在线观看 | www.色亚洲| 国产区小视频 | 中文字幕不卡在线 | 亚洲一区二区三区观看 | 国产精品普通话 | 在线播放你懂的 | 色妞网 | 91蝌蚪少妇 | 玖玖在线资源 | 国产成人短视频在线观看 | www.欧美.com | 国产精品一区二区三区免费 | 欧美男女交配 | 久久久一级片 | 天堂综合网 | 欧美在线精品一区二区三区 | 午夜伦情 | 艳妇臀荡乳欲伦交换电影 | 在线看片国产 | 国产内射合集颜射 | 亚洲综合第一 | 天堂网ww| 国产精品一区二区三区久久 | 在线观看三级网站 | 色爽爽爽 | 亚洲欧美国产视频 | 日韩高清专区 | 免费国产视频在线观看 | 国产超碰 | 欧日韩不卡在线视频 | 青娱乐在线视频观看 | 欧美高清在线一区 | 操操操综合 | 久久在线电影 | 丝袜美腿中文字幕 | 秘密爱大尺度做爰呻吟 | 亚洲欧美另类自拍 | 成人免费毛片高清视频 | 亚洲成年人在线 | 99国产精品国产免费观看 | 色婷婷色综合 | 久久久久久福利 | 欧美激情精品久久久久久蜜臀 | 午夜视频一区 | 成人av资源站| 成人av手机在线 | 欧美一区二区三区不卡视频 | av电影在线观看不卡 | 国产三级全黄 | 亚洲aaa视频 | 国产精品久久午夜夜伦鲁鲁 | 丝袜一区二区三区四区 |