improved randShuffle as suggested by John Stark in http://code.opencv.org/issues/3730
This commit is contained in:
@@ -748,29 +748,35 @@ namespace cv
|
|||||||
{
|
{
|
||||||
|
|
||||||
template<typename T> static void
|
template<typename T> static void
|
||||||
randShuffle_( Mat& _arr, RNG& rng, double iterFactor )
|
randShuffle_( Mat& _arr, RNG& rng, double )
|
||||||
{
|
{
|
||||||
int sz = _arr.rows*_arr.cols, iters = cvRound(iterFactor*sz);
|
unsigned sz = (unsigned)_arr.total();
|
||||||
if( _arr.isContinuous() )
|
if( _arr.isContinuous() )
|
||||||
{
|
{
|
||||||
T* arr = _arr.ptr<T>();
|
T* arr = _arr.ptr<T>();
|
||||||
for( int i = 0; i < iters; i++ )
|
for( unsigned i = 0; i < sz; i++ )
|
||||||
{
|
{
|
||||||
int j = (unsigned)rng % sz, k = (unsigned)rng % sz;
|
unsigned j = (unsigned)rng % sz;
|
||||||
std::swap( arr[j], arr[k] );
|
std::swap( arr[j], arr[i] );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
CV_Assert( _arr.dims <= 2 );
|
||||||
uchar* data = _arr.ptr();
|
uchar* data = _arr.ptr();
|
||||||
size_t step = _arr.step;
|
size_t step = _arr.step;
|
||||||
|
int rows = _arr.rows;
|
||||||
int cols = _arr.cols;
|
int cols = _arr.cols;
|
||||||
for( int i = 0; i < iters; i++ )
|
for( int i0 = 0; i0 < rows; i0++ )
|
||||||
{
|
{
|
||||||
int j1 = (unsigned)rng % sz, k1 = (unsigned)rng % sz;
|
T* p = _arr.ptr<T>(i0);
|
||||||
int j0 = j1/cols, k0 = k1/cols;
|
for( int j0 = 0; j0 < cols; j0++ )
|
||||||
j1 -= j0*cols; k1 -= k0*cols;
|
{
|
||||||
std::swap( ((T*)(data + step*j0))[j1], ((T*)(data + step*k0))[k1] );
|
unsigned k1 = (unsigned)rng % sz;
|
||||||
|
int i1 = (int)(k1 / cols);
|
||||||
|
int j1 = (int)(k1 - (unsigned)i1*(unsigned)cols);
|
||||||
|
std::swap( p[j0], ((T*)(data + step*i1))[j1] );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user