SLIC超像素分割算法和目前超像素算法的比较代码实现 - 图文
更新时间:2023-09-23 16:52:01 阅读量: IT计算机 文档下载
Resource.h
//{{NO_DEPENDENCIES}}
// Microsoft Visual C++ generated include file. // Used by SLICSuperpixels.rc //
#define IDD_SLICSUPERPIXELS_DIALOG 102 #define IDR_MAINFRAME 128 #define IDC_BUTTON_CREATESUPERPIXELS 1000 #define IDC_EDIT_SPCOUNT 1001 #define IDC_EDIT2 1002 #define IDC_EDIT_COMPACTNESS 1002
// Next default values for new objects //
#ifdef APSTUDIO_INVOKED
#ifndef APSTUDIO_READONLY_SYMBOLS
#define _APS_NEXT_RESOURCE_VALUE 129 #define _APS_NEXT_COMMAND_VALUE 32771 #define _APS_NEXT_CONTROL_VALUE 1003 #define _APS_NEXT_SYMED_VALUE 101 #endif #endif
Stdafx.h
// stdafx.h : include file for standard system include files, // or project specific include files that are used frequently, // but are changed infrequently
#pragma once
#ifndef _SECURE_ATL #define _SECURE_ATL 1 #endif
#ifndef VC_EXTRALEAN
#define VC_EXTRALEAN // Exclude rarely-used stuff from Windows headers #endif
#include \
#define _ATL_CSTRING_EXPLICIT_CONSTRUCTORS // some CString constructors will be explicit
// turns off MFC's hiding of some common and often safely ignored warning messages #define _AFX_ALL_WARNINGS
#include // MFC core and standard components #include // MFC extensions
#ifndef _AFX_NO_OLE_SUPPORT
#include // MFC support for Internet Explorer 4 Common Controls #endif
#ifndef _AFX_NO_AFXCMN_SUPPORT
#include // MFC support for Windows Common Controls #endif // _AFX_NO_AFXCMN_SUPPORT
#include // MFC support for ribbons and control bars
SLIC.h
// SLIC.h: interface for the SLIC class.
//=========================================================================== // This code implements the superpixel method described in: //
// Radhakrishna Achanta, Appu Shaji, Kevin Smith, Aurelien Lucchi, Pascal Fua, and Sabine Susstrunk,
// \
// EPFL Technical Report no. 149300, June 2010.
//=========================================================================== // Copyright (c) 2012 Radhakrishna Achanta [EPFL]. All rights reserved. //=========================================================================== //////////////////////////////////////////////////////////////////////
#if !defined(_SLIC_H_INCLUDED_) #define _SLIC_H_INCLUDED_
#include
class SLIC { public:
SLIC();
virtual ~SLIC();
//============================================================================ // Superpixel segmentation for a given step size (superpixel size ~= step*step) //============================================================================
void DoSuperpixelSegmentation_ForGivenSuperpixelSize(
const unsigned int* ubuff,//Each 32 bit unsigned int contains ARGB pixel values.
const int const int int*& int&
width, height, klabels,
superpixelsize,
numlabels,
const int&
const double& compactness);
//============================================================================ // Superpixel segmentation for a given number of superpixels
//============================================================================
void DoSuperpixelSegmentation_ForGivenNumberOfSuperpixels( const unsigned int* ubuff,
const int const int int*& int&
width, height, klabels,
K,//required number of superpixels
numlabels,
const int& good value for CIELAB space
const double& compactness);//10-20 is a
//============================================================================ // Supervoxel segmentation for a given step size (supervoxel size ~= step*step*step) //============================================================================ void DoSupervoxelSegmentation(
unsigned int**&
ubuffvec,
const int& const int& const int& int**& int&
width, height, depth, klabels,
supervoxelsize,
numlabels,
const int&
private:
const double& compactness);
//============================================================================ // Save superpixel labels in a text file in raster scan order
//============================================================================ void SaveSuperpixelLabels(
const int*& const int& const int&
labels, width, height,
const string& const string&
filename, path);
//============================================================================ // Save supervoxel labels in a text file in raster scan, depth order
//============================================================================ void SaveSupervoxelLabels(
const int**& const int& const int& const int&
labels,
width, height, depth,
const string& const string&
filename, path);
//============================================================================ // Function to draw boundaries around superpixels of a given 'color'.
// Can also be used to draw boundaries around supervoxels, i.e layer by layer. //============================================================================ void DrawContoursAroundSegments(
unsigned int*& int*&
const int& const int&
segmentedImage, labels, width, height, color );
const unsigned int&
//============================================================================ // The main SLIC algorithm for generating superpixels
//============================================================================
void PerformSuperpixelSLIC(
vector
const int&
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, klabels, STEP,
edgemag,
const vector
const double&
m = 10.0);
//============================================================================ // The main SLIC algorithm for generating supervoxels
//============================================================================ void PerformSupervoxelSLIC(
vector
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, kseedsz, klabels, STEP,
const double& compactness);
//============================================================================ // Pick seeds for superpixels when step size of superpixels is given.
//============================================================================ void GetLABXYSeeds_ForGivenStepSize(
vector
const bool&
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, STEP,
perturbseeds,
const vector
//============================================================================ // Pick seeds for supervoxels
//============================================================================ void GetKValues_LABXYZ(
vector
kseedsl, kseedsa,
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
SLIC::SLIC() { }
SLIC::~SLIC() { }
//============================================================================== /// RGB2XYZ ///
if(m_lvecvec) { }
if(m_avecvec) { }
if(m_bvecvec) { }
for( int d = 0; d < m_depth; d++ ) delete [] m_bvecvec[d]; delete [] m_bvecvec;
for( int d = 0; d < m_depth; d++ ) delete [] m_avecvec[d]; delete [] m_avecvec;
for( int d = 0; d < m_depth; d++ ) delete [] m_lvecvec[d]; delete [] m_lvecvec; if(m_lvec) delete [] m_lvec; if(m_avec) delete [] m_avec; if(m_bvec) delete [] m_bvec; m_lvecvec = NULL; m_avecvec = NULL; m_bvecvec = NULL; m_lvec = NULL; m_avec = NULL; m_bvec = NULL;
/// sRGB (D65 illuninant assumption) to XYZ conversion
//============================================================================== void SLIC::RGB2XYZ( { }
//=========================================================================== /// RGB2LAB
//===========================================================================
void SLIC::RGB2LAB(const int& sR, const int& sG, const int& sB, double& lval, double& aval, double& bval) {
//------------------------ //------------------------ // sRGB to XYZ conversion //------------------------ double X, Y, Z;
RGB2XYZ(sR, sG, sB, X, Y, Z);
X = r*0.4124564 + g*0.3575761 + b*0.1804375; Y = r*0.2126729 + g*0.7151522 + b*0.0721750; Z = r*0.0193339 + g*0.1191920 + b*0.9503041; if(R <= 0.04045) r = R/12.92; else else else
r = pow((R+0.055)/1.055,2.4); g = pow((G+0.055)/1.055,2.4); b = pow((B+0.055)/1.055,2.4);
if(G <= 0.04045) g = G/12.92; if(B <= 0.04045) b = B/12.92; double r, g, b; double R = sR/255.0; double G = sG/255.0; double B = sB/255.0; const int& const int& const int& double& double& double&
sR, sG, sB, X, Y, Z)
}
// XYZ to LAB conversion //------------------------
double epsilon = 0.008856; //actual CIE standard double kappa = 903.3;
//actual CIE standard
double Xr = 0.950456; //reference white double Yr = 1.0;
//reference white
double Zr = 1.088754; //reference white double xr = X/Xr; double yr = Y/Yr; double zr = Z/Zr; double fx, fy, fz;
if(xr > epsilon) fx = pow(xr, 1.0/3.0); else else else
fx = (kappa*xr + 16.0)/116.0; fy = (kappa*yr + 16.0)/116.0; fz = (kappa*zr + 16.0)/116.0;
if(yr > epsilon) fy = pow(yr, 1.0/3.0); if(zr > epsilon) fz = pow(zr, 1.0/3.0);
lval = 116.0*fy-16.0; aval = 500.0*(fx-fy); bval = 200.0*(fy-fz);
//=========================================================================== /// DoRGBtoLABConversion ///
/// For whole image: overlaoded floating point version
//=========================================================================== void SLIC::DoRGBtoLABConversion( {
int sz = m_width*m_height; lvec = new double[sz]; avec = new double[sz]; bvec = new double[sz]; const unsigned int*& double*& double*& double*&
ubuff, lvec, avec, bvec)
}
//=========================================================================== /// DoRGBtoLABConversion ///
/// For whole volume
//=========================================================================== void SLIC::DoRGBtoLABConversion( { }
//================================================================================= /// DrawContoursAroundSegments ///
/// Internal contour drawing option exists. One only needs to comment the if /// statement inside the loop that looks at neighbourhood.
}
}
RGB2LAB( r, g, b, lvec[d][j], avec[d][j], bvec[d][j] );
int sz = m_width*m_height; for( int d = 0; d < m_depth; d++ ) {
for( int j = 0; j < sz; j++ ) {
int r = (ubuff[d][j] >> 16) & 0xFF; int g = (ubuff[d][j] >> 8) & 0xFF; int b = (ubuff[d][j] ) & 0xFF;
unsigned int**& double**& double**& double**&
ubuff,
lvec, avec, bvec)
}
RGB2LAB( r, g, b, lvec[j], avec[j], bvec[j] ); for( int j = 0; j < sz; j++ ) {
int r = (ubuff[j] >> 16) & 0xFF; int g = (ubuff[j] >> 8) & 0xFF; int b = (ubuff[j] ) & 0xFF;
//================================================================================= void SLIC::DrawContoursAroundSegments( {
/* int sz = width*height;
}
if( np > 1 )//change to 2 or 3 for thinner lines { }
ubuff[mainindex] = color; istaken[mainindex] = true; }
if( false == istaken[index] )//comment this to obtain internal contours { }
if( labels[mainindex] != labels[index] ) np++;
if( (x >= 0 && x < width) && (y >= 0 && y < height) ) {
int index = y*width + x;
int mainindex(0);
for( int j = 0; j < height; j++ ) {
for( int k = 0; k < width; k++ ) {
int np(0);
for( int i = 0; i < 8; i++ ) {
int x = k + dx8[i]; int y = j + dy8[i];
vector
const int dx8[8] = {-1, -1, 0, 1, 1, 1, 0, -1}; const int dy8[8] = { 0, -1, -1, -1, 0, 1, 1, 1}; unsigned int*& int*&
const int& const int&
ubuff, labels, width, height,
color )
const unsigned int&
}*/
}
mainindex++;
int sz = width*height;
vector
vector
for( int k = 0; k < width; k++ ) { }
int np(0);
for( int i = 0; i < 8; i++ ) { }
if( np > 1 ) { }
mainindex++;
contourx[cind] = k; contoury[cind] = j; istaken[mainindex] = true; //img[mainindex] = color; cind++;
int x = k + dx8[i]; int y = j + dy8[i];
if( (x >= 0 && x < width) && (y >= 0 && y < height) ) { }
int index = y*width + x;
//if( false == istaken[index] )//comment this to obtain internal contours { }
if( labels[mainindex] != labels[index] ) np++;
}
int numboundpix = cind;//int(contourx.size()); for( int j = 0; j < numboundpix; j++ ) { }
int ii = contoury[j]*width + contourx[j]; ubuff[ii] = 0xffffff; for( int n = 0; n < 8; n++ ) { }
int x = contourx[j] + dx8[n]; int y = contoury[j] + dy8[n];
if( (x >= 0 && x < width) && (y >= 0 && y < height) ) { }
int ind = y*width + x;
if(!istaken[ind]) ubuff[ind] = 0;
//============================================================================== /// DetectLabEdges
//============================================================================== void SLIC::DetectLabEdges( {
double dx = (lvec[i-1]-lvec[i+1])*(lvec[i-1]-lvec[i+1]) +
edges.resize(sz,0);
for( int j = 1; j < height-1; j++ ) {
for( int k = 1; k < width-1; k++ ) {
int i = j*width+k;
int sz = width*height; const double* const double* const double* const int& const int&
lvec, avec, bvec,
width, height, edges)
vector
}
}
}
(avec[i-1]-avec[i+1])*(avec[i-1]-avec[i+1]) + (bvec[i-1]-bvec[i+1])*(bvec[i-1]-bvec[i+1]);
double dy = (lvec[i-width]-lvec[i+width])*(lvec[i-width]-lvec[i+width]) +
(avec[i-width]-avec[i+width])*(avec[i-width]-avec[i+width]) + (bvec[i-width]-bvec[i+width])*(bvec[i-width]-bvec[i+width]);
//edges[i] = fabs(dx) + fabs(dy); edges[i] = dx*dx + dy*dy;
//=========================================================================== /// PerturbSeeds
//=========================================================================== void SLIC::PerturbSeeds( {
int storeind = oind;
for( int i = 0; i < 8; i++ ) {
int nx = ox+dx8[i];//new x int ny = oy+dy8[i];//new y
for( int n = 0; n < numseeds; n++ ) {
int ox = kseedsx[n];//original x int oy = kseedsy[n];//original y int oind = oy*m_width + ox;
const int dx8[8] = {-1, -1, 0, 1, 1, 1, 0, -1}; const int dy8[8] = { 0, -1, -1, -1, 0, 1, 1, 1};
int numseeds = kseedsl.size(); vector
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy,
const vector
}
}
}
if( nx >= 0 && nx < m_width && ny >= 0 && ny < m_height) { }
int nind = ny*m_width + nx; if( edges[nind] < edges[storeind]) { }
storeind = nind;
if(storeind != oind) { }
kseedsx[n] = storeind%m_width; kseedsy[n] = storeind/m_width; kseedsl[n] = m_lvec[storeind]; kseedsa[n] = m_avec[storeind]; kseedsb[n] = m_bvec[storeind];
//=========================================================================== /// GetLABXYSeeds_ForGivenStepSize ///
/// The k seed values are taken as uniform spatial pixel samples.
//=========================================================================== void SLIC::GetLABXYSeeds_ForGivenStepSize(
vector
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, STEP,
perturbseeds,
const int&
const bool& {
const vector
//int xstrips = m_width/STEP; int numseeds(0); int n(0);
//int ystrips = m_height/STEP;
int xstrips = (0.5+double(m_width)/double(STEP)); int ystrips = (0.5+double(m_height)/double(STEP));
int xerr = m_width - STEP*xstrips;if(xerr < 0){xstrips--;xerr = m_width - STEP*xstrips;} int yerr = m_height - STEP*ystrips;if(yerr < 0){ystrips--;yerr = m_height- STEP*ystrips;}
for( int y = 0; y < ystrips; y++ ) {
int ye = y*yerrperstrip;
for( int x = 0; x < xstrips; x++ ) {
int xe = x*xerrperstrip;
int xoff = STEP/2; int yoff = STEP/2;
//------------------------- numseeds = xstrips*ystrips; //------------------------- kseedsl.resize(numseeds); kseedsa.resize(numseeds); kseedsb.resize(numseeds); kseedsx.resize(numseeds); kseedsy.resize(numseeds);
double xerrperstrip = double(xerr)/double(xstrips); double yerrperstrip = double(yerr)/double(ystrips);
int seedx = (x*STEP+xoff+xe);
if(hexgrid){ seedx = x*STEP+(xoff<<(y&0x1))+xe; seedx = min(m_width-1,seedx); }//for hex grid sampling int seedy = (y*STEP+yoff+ye); int i = seedy*m_width + seedx;
kseedsl[n] = m_lvec[i]; kseedsa[n] = m_avec[i]; kseedsb[n] = m_bvec[i];
kseedsx[n] = seedx; kseedsy[n] = seedy;
}
}
n++;
}
//=========================================================================== /// GetKValues_LABXYZ ///
/// The k seed values are taken as uniform spatial pixel samples.
//=========================================================================== void SLIC::GetKValues_LABXYZ( {
const bool hexgrid = false;
int xerr = m_width - STEP*xstrips;if(xerr < 0){xstrips--;xerr = m_width - STEP*xstrips;} int yerr = m_height - STEP*ystrips;if(yerr < 0){ystrips--;yerr = m_height- STEP*ystrips;} int zerr = m_depth - STEP*zstrips;if(zerr < 0){zstrips--;zerr = m_depth - STEP*zstrips;}
int xoff = STEP/2; int yoff = STEP/2; int zoff = STEP/2;
double xerrperstrip = double(xerr)/double(xstrips); double yerrperstrip = double(yerr)/double(ystrips); double zerrperstrip = double(zerr)/double(zstrips); int xstrips = (0.5+double(m_width)/double(STEP)); int ystrips = (0.5+double(m_height)/double(STEP)); int zstrips = (0.5+double(m_depth)/double(STEP)); int numseeds(0); int n(0);
vector
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, kseedsz, STEP)
if(perturbseeds) { }
PerturbSeeds(kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, edgemag);
const int&
}
//-------------------------
numseeds = xstrips*ystrips*zstrips; //------------------------- kseedsl.resize(numseeds); kseedsa.resize(numseeds); kseedsb.resize(numseeds); kseedsx.resize(numseeds); kseedsy.resize(numseeds); kseedsz.resize(numseeds);
for( int z = 0; z < zstrips; z++ ) { }
int ze = z*zerrperstrip; int d = (z*STEP+zoff+ze);
for( int y = 0; y < ystrips; y++ ) { }
int ye = y*yerrperstrip;
for( int x = 0; x < xstrips; x++ ) { }
int xe = x*xerrperstrip;
int i = (y*STEP+yoff+ye)*m_width + (x*STEP+xoff+xe);
kseedsl[n] = m_lvecvec[d][i]; kseedsa[n] = m_avecvec[d][i]; kseedsb[n] = m_bvecvec[d][i]; kseedsx[n] = (x*STEP+xoff+xe); kseedsy[n] = (y*STEP+yoff+ye); kseedsz[n] = d; n++;
//=========================================================================== /// PerformSuperpixelSLIC ///
/// Performs k mean segmentation. It is fast because it looks locally, not /// over the entire image.
//=========================================================================== void SLIC::PerformSuperpixelSLIC(
vector
M)
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, STEP,
int*& klabels,
const int& {
const double&
const vector
int sz = m_width*m_height; const int numk = kseedsl.size(); //---------------- int offset = STEP; //----------------
vector
vector
for( int itr = 0; itr < 10; itr++ ) {
distvec.assign(sz, DBL_MAX); for( int n = 0; n < numk; n++ ) {
kseedsy[n]-offset);
kseedsy[n]+offset); kseedsx[n]-offset);
//if(STEP < 8) offset = STEP*1.5;//to prevent a crash due to a very small step size
y1 = max(0.0, x1 = max(0.0,
y2 = min((double)m_height,
x2 = min((double)m_width,
sigmal.assign(numk, 0); sigmaa.assign(numk, 0); }
}
}
if( dist < distvec[i] ) { }
distvec[i] = dist; klabels[i] = n;
distxy =
dist =
l = m_lvec[i]; a = m_avec[i]; b = m_bvec[i];
for( int y = y1; y < y2; y++ ) {
for( int x = x1; x < x2; x++ ) {
int i = y*m_width + x;
kseedsx[n]+offset);
(l - kseedsl[n])*(l - kseedsl[n]) + (a - kseedsa[n])*(a - kseedsa[n]) + (b - kseedsb[n])*(b - kseedsb[n]);
(x - kseedsx[n])*(x - kseedsx[n]) +
(y - kseedsy[n])*(y - kseedsy[n]);
//------------------------------------------------------------------------
dist += distxy*invwt;//dist = sqrt(dist) + sqrt(distxy*invwt);//this is
more exact
//------------------------------------------------------------------------
//----------------------------------------------------------------- // Recalculate the centroid and store in the seed values
//----------------------------------------------------------------- //instead of reassigning memory on each iteration, just reset.
sigmab.assign(numk, 0); sigmax.assign(numk, 0); sigmay.assign(numk, 0); clustersize.assign(numk, 0);
//------------------------------------ //edgesum.assign(numk, 0);
//------------------------------------ {int ind(0);
for( int r = 0; r < m_height; r++ ) { }}
{for( int k = 0; k < numk; k++ ) { }}
{for( int k = 0; k < numk; k++ ) {
kseedsl[k] = sigmal[k]*inv[k]; kseedsa[k] = sigmaa[k]*inv[k]; kseedsb[k] = sigmab[k]*inv[k]; kseedsx[k] = sigmax[k]*inv[k]; kseedsy[k] = sigmay[k]*inv[k];
//------------------------------------ //edgesum[k] *= inv[k];
if( clustersize[k] <= 0 ) clustersize[k] = 1;
inv[k] = 1.0/clustersize[k];//computing inverse now to multiply, than divide later for( int c = 0; c < m_width; c++ ) { }
sigmal[klabels[ind]] += m_lvec[ind]; sigmaa[klabels[ind]] += m_avec[ind]; sigmab[klabels[ind]] += m_bvec[ind]; sigmax[klabels[ind]] += c; sigmay[klabels[ind]] += r;
//------------------------------------ //edgesum[klabels[ind]] += edgemag[ind]; //------------------------------------ clustersize[klabels[ind]] += 1.0; ind++;
}
}
}}
//------------------------------------
//=========================================================================== /// PerformSupervoxelSLIC ///
/// Performs k mean segmentation. It is fast because it searches locally, not /// over the entire image.
//=========================================================================== void SLIC::PerformSupervoxelSLIC(
vector
kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, kseedsz, klabels, STEP,
int**& {
const int&
const double&
compactness)
int sz = m_width*m_height; const int numk = kseedsl.size();
//int numitr(0);
//---------------- int offset = STEP; //----------------
vector
vector
//if(STEP < 8) offset = STEP*1.5;//to prevent a crash due to a very small step size
vector< double > initdouble(sz, DBL_MAX);
vector< vector
double invwt = 1.0/((STEP/compactness)*(STEP/compactness));//compactness = 20.0 is usually
good.
int x1, y1, x2, y2, z1, z2; double l, a, b; double dist; double distxyz;
for( int itr = 0; itr < 5; itr++ ) {
distvec.assign(m_depth, initdouble); for( int n = 0; n < numk; n++ ) {
kseedsy[n]-offset);
kseedsy[n]+offset); kseedsx[n]+offset); kseedsz[n]+offset); kseedsx[n]-offset); kseedsz[n]-offset);
y1 = max(0.0, x1 = max(0.0, z1 = max(0.0,
distxyz =
dist =
y2 = min((double)m_height, x2 = min((double)m_width, z2 = min((double)m_depth,
for( int z = z1; z < z2; z++ ) {
for( int y = y1; y < y2; y++ ) {
for( int x = x1; x < x2; x++ ) {
int i = y*m_width + x; l = m_lvecvec[z][i]; a = m_avecvec[z][i]; b = m_bvecvec[z][i];
(l - kseedsl[n])*(l - kseedsl[n]) + (a - kseedsa[n])*(a - kseedsa[n]) + (b - kseedsb[n])*(b - kseedsb[n]); (x - kseedsx[n])*(x - kseedsx[n]) +
}
}
}
(y - kseedsy[n])*(y - kseedsy[n]) + (z - kseedsz[n])*(z - kseedsz[n]);
//------------------------------------------------------------------------
dist += distxyz*invwt;
//------------------------------------------------------------------------
}
if( dist < distvec[z][i] ) { }
distvec[z][i] = dist; klabels[z][i] = n;
//----------------------------------------------------------------- // Recalculate the centroid and store in the seed values
//----------------------------------------------------------------- //instead of reassigning memory on each iteration, just reset. sigmal.assign(numk, 0); sigmaa.assign(numk, 0); sigmab.assign(numk, 0); sigmax.assign(numk, 0); sigmay.assign(numk, 0); sigmaz.assign(numk, 0); clustersize.assign(numk, 0); for( int d = 0; d < m_depth; d++ ) {
int ind(0);
for( int r = 0; r < m_height; r++ ) {
for( int c = 0; c < m_width; c++ ) {
sigmal[klabels[d][ind]] += m_lvecvec[d][ind]; sigmaa[klabels[d][ind]] += m_avecvec[d][ind]; sigmab[klabels[d][ind]] += m_bvecvec[d][ind]; sigmax[klabels[d][ind]] += c; sigmay[klabels[d][ind]] += r;
}
}
}
}
}
sigmaz[klabels[d][ind]] += d; clustersize[klabels[d][ind]] += 1.0; ind++;
{for( int k = 0; k < numk; k++ ) { }}
{for( int k = 0; k < numk; k++ ) { }}
kseedsl[k] = sigmal[k]*inv[k]; kseedsa[k] = sigmaa[k]*inv[k]; kseedsb[k] = sigmab[k]*inv[k]; kseedsx[k] = sigmax[k]*inv[k]; kseedsy[k] = sigmay[k]*inv[k]; kseedsz[k] = sigmaz[k]*inv[k];
if( clustersize[k] <= 0 ) clustersize[k] = 1;
inv[k] = 1.0/clustersize[k];//computing inverse now to multiply, than divide later
//=========================================================================== /// SaveSuperpixelLabels ///
/// Save labels in raster scan order.
//=========================================================================== void SLIC::SaveSuperpixelLabels( {
#ifdef WINDOWS
char fname[256];
const int*& const int& const int&
labels, width, height,
const string& const string&
filename, path)
char extn[256];
_splitpath(filename.c_str(), NULL, NULL, fname, extn); string temp = fname;
string finalpath = path + temp + string(\); #else
string nameandextension = filename; size_t pos = filename.find_last_of(\);
if(pos != string::npos)//if a slash is found, then take the filename with extension {
nameandextension = filename.substr(pos+1); }
string newname = nameandextension.replace(nameandextension.rfind(\)+1, 3, \);//find the position of the dot and replace the 3 characters following it. string finalpath = path+newname; #endif
int sz = width*height; }
//=========================================================================== /// SaveSupervoxelLabels ///
/// Save labels in raster scan order.
//=========================================================================== void SLIC::SaveSupervoxelLabels( {
#ifdef WINDOWS
const int**& const int& const int& const int&
labels,
width, height, depth,
ofstream outfile;
outfile.open(finalpath.c_str(), ios::binary); for( int i = 0; i < sz; i++ ) { }
outfile.close();
outfile.write((const char*)&labels[i], sizeof(int));
const string& const string&
filename, path)
char fname[256]; char extn[256];
_splitpath(filename.c_str(), NULL, NULL, fname, extn); string temp = fname;
string finalpath = path + temp + string(\); #else
string nameandextension = filename; size_t pos = filename.find_last_of(\);
if(pos != string::npos)//if a slash is found, then take the filename with extension {
nameandextension = filename.substr(pos+1); }
string newname = nameandextension.replace(nameandextension.rfind(\)+1, 3, \);//find the position of the dot and replace the 3 characters following it. string finalpath = path+newname; #endif
int sz = width*height; }
//=========================================================================== /// EnforceLabelConnectivity /// /// /// ///
1. finding an adjacent label for each new component at the start 2. if a certain component is too small, assigning the previously found adjacent label to this component, and not incrementing the label. ofstream outfile;
outfile.open(finalpath.c_str(), ios::binary); for( int d = 0; d < depth; d++ ) { }
outfile.close();
for( int i = 0; i < sz; i++ ) { }
outfile.write((const char*)&labels[d][i], sizeof(int));
//=========================================================================== void SLIC::EnforceLabelConnectivity(
const int* const int
labels,//input labels that need to be corrected to remove width,
stray labels
{
const int int*& int&
height,
nlabels,//new labels
numlabels,//the number of labels changes in the end if segments
K) //the number of superpixels desired by the user
are removed
const int&
// const int dx8[8] = {-1, -1, 0, 1, 1, 1, 0, -1}; // const int dy8[8] = { 0, -1, -1, -1, 0, 1, 1, 1};
const int sz = width*height; const int SUPSZ = sz/K; //nlabels.resize(sz, -1);
for( int i = 0; i < sz; i++ ) nlabels[i] = -1; int label(0);
int* xvec = new int[sz]; int* yvec = new int[sz]; int oindex(0);
int adjlabel(0);//adjacent label for( int j = 0; j < height; j++ ) {
for( int k = 0; k < width; k++ ) {
if( 0 > nlabels[oindex] ) {
nlabels[oindex] = label; //-------------------- // Start a new segment //-------------------- xvec[0] = k; yvec[0] = j;
//------------------------------------------------------- // Quickly find an adjacent label for use later if needed //------------------------------------------------------- {for( int n = 0; n < 4; n++ ) {
int x = xvec[0] + dx4[n]; int y = yvec[0] + dy4[n];
if( (x >= 0 && x < width) && (y >= 0 && y < height) )
const int dx4[4] = {-1, 0, 1, 0}; const int dy4[4] = { 0, -1, 0, 1};
}}
{ }
int nindex = y*width + x;
if(nlabels[nindex] >= 0) adjlabel = nlabels[nindex];
int count(1);
for( int c = 0; c < count; c++ ) { }
//------------------------------------------------------- // If segment size is less then a limit, assign an
// adjacent label found before, and decrement label count. //------------------------------------------------------- if(count <= SUPSZ >> 2) {
for( int c = 0; c < count; c++ ) { } label--;
int ind = yvec[c]*width+xvec[c]; nlabels[ind] = adjlabel; for( int n = 0; n < 4; n++ ) { }
int x = xvec[c] + dx4[n]; int y = yvec[c] + dy4[n];
if( (x >= 0 && x < width) && (y >= 0 && y < height) ) { }
int nindex = y*width + x;
if( 0 > nlabels[nindex] && labels[oindex] == labels[nindex] ) { }
xvec[count] = x; yvec[count] = y;
nlabels[nindex] = label; count++;
}
}
}
}
} label++;
oindex++;
numlabels = label; if(xvec) delete [] xvec; if(yvec) delete [] yvec;
//=========================================================================== /// RelabelStraySupervoxels
//=========================================================================== void SLIC::EnforceSupervoxelLabelConnectivity( {
int adjlabel(0);//adjacent label
int* xvec = new int[SUPSZ*10];//a large enough size int* yvec = new int[SUPSZ*10];//a large enough size int* zvec = new int[SUPSZ*10];//a large enough size
//------------------ // memory allocation //------------------
int** nlabels = new int*[depth]; {for( int d = 0; d < depth; d++ ) {
int sz = width*height;
const int SUPSZ = STEP*STEP*STEP;
const int dx10[10] = {-1, 0, 1, 0, -1, 1, 1, -1, 0, 0}; const int dy10[10] = { 0, -1, 0, 1, -1, -1, 1, 1, 0, 0}; const int dz10[10] = { 0, 0, 0, 0, 0, 0, 0, 0, -1, 1}; int**& const int& const int& const int& int&
const int&
labels,//input - previous labels, output - new labels width, height, depth, STEP)
numlabels,
}}
nlabels[d] = new int[sz];
for( int i = 0; i < sz; i++ ) nlabels[d][i] = -1;
//------------------ // labeling
//------------------ int lab(0);
{for( int d = 0; d < depth; d++ ) {
int i(0);
for( int h = 0; h < height; h++ ) {
for( int w = 0; w < width; w++ ) {
if(nlabels[d][i] < 0) {
nlabels[d][i] = lab;
//------------------------------------------------------- // Quickly find an adjacent label for use later if needed //------------------------------------------------------- {for( int n = 0; n < 10; n++ ) { }}
xvec[0] = w; yvec[0] = h; zvec[0] = d; int count(1);
for( int c = 0; c < count; c++ ) {
for( int n = 0; n < 10; n++ ) int x = w + dx10[n]; int y = h + dy10[n]; int z = d + dz10[n];
if( (x >= 0 && x < width) && (y >= 0 && y < height) && (z >= 0 && { }
int nindex = y*width + x; if(nlabels[z][nindex] >= 0) { }
adjlabel = nlabels[z][nindex];
z < depth) )
}
}
{ }
int x = xvec[c] + dx10[n]; int y = yvec[c] + dy10[n]; int z = zvec[c] + dz10[n];
if( (x >= 0 && x < width) && (y >= 0 && y < height) && (z >= 0 { }
int nindex = y*width + x;
if( 0 > nlabels[z][nindex] && labels[d][i] == { }
xvec[count] = x; yvec[count] = y; zvec[count] = z;
nlabels[z][nindex] = lab; count++;
&& z < depth))
labels[z][nindex] )
//------------------------------------------------------- // If segment size is less then a limit, assign an
// adjacent label found before, and decrement label count. //-------------------------------------------------------
if(count <= (SUPSZ >> 2))//this threshold can be changed according to { }
//-------------------------------------------------------- lab++;
for( int c = 0; c < count; c++ ) { } lab--;
int ind = yvec[c]*width+xvec[c]; nlabels[zvec[c]][ind] = adjlabel;
needs
i++;
}
}}
}
}
//------------------ // mem de-allocation //------------------
{for( int d = 0; d < depth; d++ ) { }}
{for( int d = 0; d < depth; d++ ) { }}
delete [] nlabels; //------------------ if(xvec) delete [] xvec; if(yvec) delete [] yvec; if(zvec) delete [] zvec; //------------------ numlabels = lab; //------------------
delete [] nlabels[d];
for( int i = 0; i < sz; i++ ) labels[d][i] = nlabels[d][i];
//=========================================================================== /// DoSuperpixelSegmentation_ForGivenSuperpixelSize ///
/// The input parameter ubuff conains RGB values in a 32-bit unsigned integers /// as follows: ///
/// [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] ///
/// Nothing R G B ///
/// The RGB values are accessed from (and packed into) the unsigned integers /// using bitwise operators as can be seen in the function DoRGBtoLABConversion(). ///
/// compactness value depends on the input pixels values. For instance, if /// the input is greyscale with values ranging from 0-100, then a compactness /// value of 20.0 would give good results. A greater value will make the /// superpixels more compact while a smaller value would make them more uneven.
///
/// The labels can be saved if needed using SaveSuperpixelLabels()
//=========================================================================== void SLIC::DoSuperpixelSegmentation_ForGivenSuperpixelSize( const unsigned int* ubuff,
const int const int int*& int&
width, height, klabels, superpixelsize,
numlabels,
const int& {
const double& compactness)
//------------------------------------------------ const int STEP = sqrt(double(superpixelsize))+0.5; //------------------------------------------------
//-------------------------------------------------- m_width = width; m_height = height;
int sz = m_width*m_height; //klabels.resize( sz, -1 );
//-------------------------------------------------- klabels = new int[sz];
for( int s = 0; s < sz; s++ ) klabels[s] = -1; vector
//-------------------------------------------------- if(1)//LAB, the default option {
DoRGBtoLABConversion(ubuff, m_lvec, m_avec, m_bvec); }
else//RGB {
m_lvec = new double[sz]; m_avec = new double[sz]; m_bvec = new double[sz]; for( int i = 0; i < sz; i++ ) {
m_lvec[i] = ubuff[i] >> 16 & 0xff; m_avec[i] = ubuff[i] >> 8 & 0xff;
m_bvec[i] = ubuff[i] & 0xff; } }
//--------------------------------------------------
bool perturbseeds(false);//perturb seeds is not absolutely necessary, one can set this flag to false }
//=========================================================================== /// DoSuperpixelSegmentation_ForGivenNumberOfSuperpixels ///
/// The input parameter ubuff conains RGB values in a 32-bit unsigned integers /// as follows: ///
/// [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] ///
/// Nothing R G B ///
/// The RGB values are accessed from (and packed into) the unsigned integers /// using bitwise operators as can be seen in the function DoRGBtoLABConversion(). ///
/// compactness value depends on the input pixels values. For instance, if /// the input is greyscale with values ranging from 0-100, then a compactness /// value of 20.0 would give good results. A greater value will make the /// superpixels more compact while a smaller value would make them more uneven. ///
/// The labels can be saved if needed using SaveSuperpixelLabels()
int* nlabels = new int[sz];
EnforceLabelConnectivity(klabels, m_width, m_height, nlabels, numlabels, {for(int i = 0; i < sz; i++ ) klabels[i] = nlabels[i];} if(nlabels) delete [] nlabels;
PerformSuperpixelSLIC(kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, klabels, STEP, numlabels = kseedsl.size(); edgemag,compactness);
vector
if(perturbseeds) DetectLabEdges(m_lvec, m_avec, m_bvec, m_width, m_height, edgemag); GetLABXYSeeds_ForGivenStepSize(kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, STEP,
perturbseeds, edgemag);
double(sz)/double(STEP*STEP));
//=========================================================================== void SLIC::DoSuperpixelSegmentation_ForGivenNumberOfSuperpixels( const unsigned int* ubuff,
const int const int int*& int&
width, height, klabels,
K,//required number of superpixels
numlabels,
const int&
const double& compactness)//weight given to spatial distance {
const int superpixelsize = 0.5+double(width*height)/double(K);
DoSuperpixelSegmentation_ForGivenSuperpixelSize(ubuff,width,height,klabels,numlabels,superpixelsize,compactness); }
//=========================================================================== /// DoSupervoxelSegmentation ///
/// There is option to save the labels if needed. ///
/// The input parameter ubuffvec holds all the video frames. It is a
/// 2-dimensional array. The first dimension is depth and the second dimension /// is pixel location in a frame. For example, to access a pixel in the 3rd /// frame (i.e. depth index 2), in the 4th row (i.e. height index 3) on the /// 37th column (i.e. width index 36), you would write: ///
/// unsigned int the_pixel_i_want = ubuffvec[2][3*width + 36] ///
/// In addition, here is how the RGB values are contained in a 32-bit unsigned /// integer: ///
/// [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] [1 1 1 1 1 1 1 1] ///
/// Nothing R G B ///
/// The RGB values are accessed from (and packed into) the unsigned integers /// using bitwise operators as can be seen in the function DoRGBtoLABConversion(). ///
/// compactness value depends on the input pixels values. For instance, if
/// the input is greyscale with values ranging from 0-100, then a compactness /// value of 20.0 would give good results. A greater value will make the /// supervoxels more compact while a smaller value would make them more uneven. //=========================================================================== void SLIC::DoSupervoxelSegmentation(
unsigned int**& const int& const int& const int& int**& int&
ubuffvec, width, height, depth, klabels, supervoxelsize,
numlabels,
const int& {
const double& compactness)
//--------------------------------------------------------- const int STEP = 0.5 + pow(double(supervoxelsize),1.0/3.0); //---------------------------------------------------------
//-------------------------------------------------- m_width = width; m_height = height; m_depth = depth;
int sz = m_width*m_height;
//-------------------------------------------------- m_lvecvec = new double*[depth]; m_avecvec = new double*[depth]; m_bvecvec = new double*[depth]; for( int d = 0; d < depth; d++ ) {
m_lvecvec[d] = new double[sz]; m_avecvec[d] = new double[sz]; m_bvecvec[d] = new double[sz]; vector
//klabels = new int*[depth];
//klabels[d] = new int[sz];
}
}
for( int s = 0; s < sz; s++ ) { }
klabels[d][s] = -1;
DoRGBtoLABConversion(ubuffvec, m_lvecvec, m_avecvec, m_bvecvec);
GetKValues_LABXYZ(kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, kseedsz, STEP);
PerformSupervoxelSLIC(kseedsl, kseedsa, kseedsb, kseedsx, kseedsy, kseedsz, klabels, STEP,
compactness);
EnforceSupervoxelLabelConnectivity(klabels, width, height, depth, numlabels, STEP);
SLICSuperpixels.cpp
// SLICSuperpixels.cpp : Defines the class behaviors for the application. //
#include \
#include \ #include \
#ifdef _DEBUG
#define new DEBUG_NEW #endif
// CSLICSuperpixelsApp
BEGIN_MESSAGE_MAP(CSLICSuperpixelsApp, CWinAppEx)
// CSLICSuperpixelsApp construction
ON_COMMAND(ID_HELP, &CWinApp::OnHelp) END_MESSAGE_MAP()
CSLICSuperpixelsApp::CSLICSuperpixelsApp() { }
// The one and only CSLICSuperpixelsApp object
CSLICSuperpixelsApp theApp;
// CSLICSuperpixelsApp initialization
BOOL CSLICSuperpixelsApp::InitInstance() {
CSLICSuperpixelsDlg dlg; m_pMainWnd = &dlg;
INT_PTR nResponse = dlg.DoModal(); if (nResponse == IDOK) { }
else if (nResponse == IDCANCEL) { }
// TODO: Place code here to handle when the dialog is // dismissed with Cancel
// TODO: Place code here to handle when the dialog is // dismissed with OK // Standard initialization
// If you are not using these features and wish to reduce the size // of your final executable, you should remove from the following // the specific initialization routines you do not need // Change the registry key under which our settings are stored // TODO: You should modify this string to be something appropriate // such as the name of your company or organization
SetRegistryKey(_T(\)); CWinAppEx::InitInstance();
// TODO: add construction code here,
// Place all significant initialization in InitInstance
}
// Since the dialog has been closed, return FALSE so that we exit the // application, rather than start the application's message pump. return FALSE;
SLICSuperpixelsDlg.cpp
// SLICSuperpixelsDlg.cpp : implementation file //
#include \
#include \ #include \ #include \ #include \
#ifdef _DEBUG
#define new DEBUG_NEW #endif
// CSLICSuperpixelsDlg dialog
CSLICSuperpixelsDlg::CSLICSuperpixelsDlg(CWnd* pParent /*=NULL*/) { }
void CSLICSuperpixelsDlg::DoDataExchange(CDataExchange* pDX) {
CDialog::DoDataExchange(pDX);
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME); : CDialog(CSLICSuperpixelsDlg::IDD, pParent) , m_spcount(0) , m_compactness(0)
}
DDX_Text(pDX, IDC_EDIT_SPCOUNT, m_spcount); DDV_MinMaxInt(pDX, m_spcount, 1, 10000000);
DDX_Text(pDX, IDC_EDIT_COMPACTNESS, m_compactness); DDV_MinMaxDouble(pDX, m_compactness, 1.0, 80.0);
BEGIN_MESSAGE_MAP(CSLICSuperpixelsDlg, CDialog)
// CSLICSuperpixelsDlg message handlers
BOOL CSLICSuperpixelsDlg::OnInitDialog() { }
void CSLICSuperpixelsDlg::OnEnChangeEditSpcount() {
// TODO: If this is a RICHEDIT control, the control will not
// send this notification unless you override the CDialog::OnInitDialog() // function and call CRichEditCtrl().SetEventMask()
return TRUE; // return TRUE unless you set the focus to a control // TODO: Add extra initialization here m_spcount = 200; m_compactness = 10.0;
UpdateData(FALSE);//FALSE to set data, TRUE to retrieve data
// Set the icon for this dialog. The framework does this automatically // when the application's main window is not a dialog SetIcon(m_hIcon, TRUE);
// Set big icon
SetIcon(m_hIcon, FALSE);
// Set small icon
CDialog::OnInitDialog(); ON_WM_PAINT()
ON_WM_QUERYDRAGICON() //}}AFX_MSG_MAP
ON_BN_CLICKED(IDC_BUTTON_CREATESUPERPIXELS,
ON_EN_CHANGE(IDC_EDIT_SPCOUNT, &CSLICSuperpixelsDlg::OnEnChangeEditSpcount)
ON_EN_CHANGE(IDC_EDIT_COMPACTNESS, &CSLICSuperpixelsDlg::OnEnChangeEditCompactness)
&CSLICSuperpixelsDlg::OnBnClickedButtonCreatesuperpixels)
END_MESSAGE_MAP()
正在阅读:
SLIC超像素分割算法和目前超像素算法的比较代码实现 - 图文09-23
酒店祝福语02-24
2014一注建筑师物理试题整理版(求正解) - 图文09-16
微生物学实验11-09
新入职员工个人总结(实用24篇)03-26
2017年江苏省测绘职业技能鉴定《工程测量员》试题10-11
雷特磁力钻都参数,都找齐了,分享07-20
漆黑的魅影5.0攻略 - 图文03-18
2004雅典奥运金牌榜07-18
航海英语题库2580完整翻译版04-27
- 供应商绩效评价考核程序
- 美国加州水资源开发管理历史与现状的启示
- 供应商主数据最终用户培训教材
- 交通安全科普体验教室施工方案
- 井架安装顺序
- 会员积分制度
- 互联网对美容连锁企业的推动作用
- 互联网发展先驱聚首香港
- 公司文档管理规则
- 机电一体化系统设计基础作业、、、参考答案
- 如何选择BI可视化工具
- 互联网产品经理必备文档技巧
- 居家装修风水的布置_家庭风水布局详解
- 全省基础教育信息化应用与发展情况调查问卷
- 中国石油--计算机网络应用基础第三阶段在线作业
- 【知识管理专题系列之五十八】知识管理中如何实现“场景化协同”
- 网络推广方案
- 中国石油--计算机网络应用基础第二阶段在线作业
- 汽车检测与维修技术专业人才培养方案
- 详解胎儿颈透明层
- 算法
- 像素
- 分割
- 目前
- 代码
- 实现
- 比较
- 图文
- SLIC
- 三线摆法测量物体的转动惯量2015
- 小学语文六年级下册第五单元测试题
- 精品课程试题库
- 2013年中考数学试卷分类汇编-反比例函数 - 图文
- 化工机器复习题2009
- 湖北省污染源自动监控系统管理办法(试行)
- 城市广场人性化设计研究
- 部编版小学二年级语文下册《小毛虫》名师教案
- 2019《微生物与人类健康》高分期末考试答案
- 地理必修中图版1.1区域和区域差异教案(教学过程一)
- 2014全国妇幼健康竞赛题 妇女保健
- 微机型自动准同期装置在电力系统中应用 - 图文
- 北京市顺义区2014届高三3月月统一测试(理综) -
- 上市公司募投项目是否需要经过招投标
- 从内外服联盟到封邦建国
- (精品)部编版三年级上册语文试题-期末试卷(AB卷)
- 学案66
- 设备运行维护技术试卷A
- 江南民居的特点1
- Java程序设计-试验2(学生版)资料