Esempio n. 1
0
float   KKB::LLoydsIndexOfPatchiness (const VectorInt& bins)
{
  // As defined by Andrew Remsen
  // also look at http://www.pmel.noaa.gov/pubs/outstand/stab1646/statistics.shtml

  if  (bins.size () < 1)
    return  0.0f;

  kkuint32  x;
  double  total = 0.0;
  double  mean  = 0.0;

  for  (x = 0;  x < bins.size ();  x++)
    total += bins[x];

  mean = total / double (bins.size ());

  double  totalDeltaSquared = 0.0;

  for  (x = 0;  x < bins.size ();  x++)
  {
    double  delta = double (bins[x]) - mean;
    totalDeltaSquared += delta * delta;
  }

  double  var = totalDeltaSquared / bins.size ();


  double  varDivMean = var / mean;
  double  oneDivMean = 1.0 / mean;

  float p =  float ((varDivMean - 1.0 + mean) * oneDivMean);

  return  p;
}  /* LLoydsIndexOfPatchiness */
Esempio n. 2
0
std::string		World::serialize(const std::vector<Vector2i> &chunkIds,
					 const std::vector<Vector2i> &positions,
					 const std::vector<Vector2i> &sizes)
{
  ProtocolMessage	msg;
  WorldZone		*worldZone = new WorldZone;
  ChunkZone		*chunkZone;
  VectorInt		*id;
  VectorUint		*position;
  VectorUint		*size;
  std::string		serialized;

  Chunk			*chunk;
  unsigned int		x;
  unsigned int		y;
  unsigned int		chunkNb;
  unsigned int		nbChunks = chunkIds.size();

  for (chunkNb = 0; chunkNb < nbChunks; ++chunkNb)
    {
      if ((chunk = getChunk(chunkIds[chunkNb])) != nullptr)
  	{
	  chunkZone = worldZone->add_chunkzone();

	  if (chunkZone == nullptr)
	    continue ;
  	  for (y = 0; y < Chunk::height; ++y)
  	    {
  	      for (x = 0; x < Chunk::width; ++x)
  		{
  		  chunkZone->add_fgtiles(static_cast<unsigned int>(chunk->getTile(x, y)));
  		}
  	    }
  	}
      else
  	continue ;
      id = new VectorInt;
      position = new VectorUint;
      size = new VectorUint;

      id->set_x(chunkIds[chunkNb].x);
      id->set_y(chunkIds[chunkNb].y);
      position->set_x(positions[chunkNb].x);
      position->set_y(positions[chunkNb].y);
      size->set_x(sizes[chunkNb].x);
      size->set_y(sizes[chunkNb].y);
      chunkZone->set_allocated_id(id);
      chunkZone->set_allocated_position(position);
      chunkZone->set_allocated_size(size);
    }
  msg.set_content(ProtocolMessage::CHUNKZONE);
  msg.set_allocated_worldzone(worldZone);
  msg.SerializeToString(&serialized);
  return serialized;
}
Esempio n. 3
0
void  ClassSummaryList::SpatialOverlapReport (ostream&  o)  const
{
  KKStr classTitle1, classTitle2;

  MLClassListPtr  classes = GetListOfClasses ();
  classes->ExtractTwoTitleLines (classTitle1, classTitle2);


  VectorInt binSizes = LLoydsBinSizes ();
  for  (kkuint32 binSizeIdx = 0;  binSizeIdx < kkuint32 (binSizes.size ());  binSizeIdx++)
  {
    kkint32  binSize = binSizes[binSizeIdx];

 
    o << endl 
      << endl 
      << endl
      << "Spatial Overlap Indexes for BinSize[" << binSize << "]" << endl
      << endl
      << "Class" << "\t" << classTitle1 << endl
      << "Name"  << "\t" << classTitle2 << endl;


    ClassSummaryList::const_iterator  idx;

    for  (idx = begin ();  idx != end ();  idx++)
    {
      ClassSummaryPtr  cs1 = *idx;

      o << cs1->ClassName ();

      ClassSummaryList::const_iterator  idx2;
      for  (idx2 = begin ();  idx2 != end ();  idx2++)
      {
        ClassSummaryPtr  cs2 = *idx2;
        if  (idx == idx2)
          o << "\t" << "-";
        else
        {
          double  spatialIndex = SpatialOverlapIndex (binSize, cs1, cs2);
          o << "\t" << spatialIndex;
        }
      }

      o << endl;
    }
  }

  delete  classes;
}  /* SpatialOverlapReport */
Esempio n. 4
0
void            Server::actDisplacement(Client *client, Action act)
{
  ClientEntity  &clEnt = client->getEntity();
  Vector2f      ratio = {CHUNKWIDTH / 256.f, CHUNKHEIGHT / 256.f};
  // to remove, let me maintain the speed

  clEnt.move(Vector2f(act == Action::Left ? -0.01 / ratio.x :
                      act == Action::Right ? 0.01 / ratio.x :
                      0,
                      act == Action::Forward ? 0.01 / ratio.y :
                      act == Action::Back ? -0.01 / ratio.y :
                      0));


  // petite partie en dur :D
  const Vector2f        &plPos = clEnt.getPosition();
  const Vector2i        &plChunk = clEnt.getChunkId();

  ProtocolMessage       msg;
  Displacement          *displacement = new Displacement;
  VectorFloat           *acceleration = new VectorFloat;
  VectorFloat           *velocity = new VectorFloat;
  Position              *position = new Position;
  VectorInt             *chunkId = new VectorInt;
  VectorFloat           *pos = new VectorFloat;
  std::string           serialized;

  // quick hard coded value
  acceleration->set_x(0);
  acceleration->set_y(0);
  velocity->set_x(0);
  velocity->set_y(0);

  chunkId->set_x(plChunk.x);
  chunkId->set_y(plChunk.y);
  pos->set_x(plPos.x);
  pos->set_y(plPos.y);
  position->set_allocated_chunkid(chunkId);
  position->set_allocated_pos(pos);

  displacement->set_allocated_acceleration(acceleration);
  displacement->set_allocated_velocity(velocity);
  displacement->set_allocated_position(position);

  msg.set_content(ProtocolMessage::DISPLACEMENT);
  msg.set_allocated_displacement(displacement);
  msg.SerializeToString(&serialized);
  client->sendPacket(0, serialized);
}
Esempio n. 5
0
Vector& Vector::
operator=( const Vector &A )
{
	if( r )
		r->unrefer();

	r = A.r->refer();

	return *this;
}
Esempio n. 6
0
VectorInt  ClassSummaryList::LLoydsBinSizes ()  const
{
  VectorInt  binSizes;

  ClassSummaryList::const_iterator  idx;
  for  (idx = begin ();  idx != end ();  idx++)
  {
    const ClassSummaryPtr  cs = *idx;
    for  (kkuint32 lloydsEntryIdx = 0;  lloydsEntryIdx < cs->NumOfLLoydsEntries ();  lloydsEntryIdx++)
    {
      LLoydsEntryPtr  lloydsEntry = cs->LLoydsEntryByIndex (lloydsEntryIdx);
      if  (lloydsEntry)
      {
        kkuint32 zed = 0;
        kkint32 binSize = lloydsEntry->LLoydsBinSize ();
        // if 'binSize' not in 'binSizes'  then add
        for  (zed = 0;  zed < kkuint32 (binSizes.size ());  zed++)
        {
          if  (binSizes[zed] == binSize)
            break;
        }
        if  (zed >= binSizes.size ())
          binSizes.push_back (binSize);
      }
    }
  }


  sort (binSizes.begin (), binSizes.end ());

  return  binSizes;
}  /* LLoydsBinSizes */
Esempio n. 7
0
void  ClassSummaryList::SummaryReport (ostream&  r)  const
{
  kkuint32  binSizeIDX = 0;


  r << "Statistic Summary by Class" << endl
    << endl;

  VectorInt  binSizes = LLoydsBinSizes ();
  r << ""           << "\t"  << ""       << "\t" << ""          << "\t" << "LLoydsIndex's" << endl;
  r << "ClassName"  << "\t"  << "U2Stat" << "\t" << "Z-Score";

  for  (binSizeIDX = 0;  binSizeIDX < binSizes.size ();  binSizeIDX++)
    r << "\t" << binSizes[binSizeIDX];
  r << endl;

  const_iterator  idx;

  for  (idx = begin ();  idx != end ();  idx++)
  {
    ClassSummaryPtr  cs = *idx;
    r << cs->ClassName () << "\t"
      << cs->U2Stat    () << "\t"
      << cs->ZScore    ();

    for  (binSizeIDX = 0;  binSizeIDX < binSizes.size ();  binSizeIDX++)
    {
      kkint32 binSize = binSizes[binSizeIDX];

      LLoydsEntryPtr  lloydsEntry = cs->LLoydsEntryByBinSize (binSize);
      if  (lloydsEntry == NULL)
        r << "\t" << "-";
      else
        r << "\t" << lloydsEntry->LLoydsIndex ();
    }
    r << endl;
  }
}  /* SummaryReport */
Esempio n. 8
0
	/* assign changes the matrix, it does not create a new one! */
double Vector::
assign( int rownum, double d )
{
	assert(r != 0);

	if( rownum > row() || rownum <= 0 ) {
	  std::cerr << "Warning: trying to assign out of bounds" << std::endl;
	  std::cerr << "row " << rownum << std::endl;
	  std::cerr << "Vector size " << row() << std::endl;
	  std::abort();
	}

	if( r->count == 1 ) {
			/* Don't need to create a new matrix, since we are the only */
			/*  one pointing to ours 									*/
	}
	else {
		VectorInt *vi = new VectorInt( *r );
		r->unrefer();
		r = vi->refer();
	}

	return d;
}
Esempio n. 9
0
void QPReconstructLambda(Vector vLambda, Vector vLambdaScale)
{
    int n=vi_QP.sz()-1, nc=vLambda.sz();
    int *ii=vi_QP;
    double *l=vLambda, *s=vLambdaScale;

    if (n>=0)
        while (nc--)
        {
            if (ii[n]==nc) 
            { 
//                l[nc]=mmax(0.0,l[n]/s[n]); 
                l[nc]=l[n]/s[n]; 
                n--; 
                if (n<0) break; 
            }
            else l[nc]=0.0;
        }
    if (nc) memset(l,0,nc*sizeof(double));
}
Esempio n. 10
0
void restartSimpleQPSolve(Vector vBO,   // in
                          Vector vP)                    // out
{
    if (bQRFailed_QP) { vP.zero(); return; }
    int i,k=0, *ii=vi_QP, nc2=vi_QP.sz();
    double *lambda=vLastLambda_QP, *b=vBO;
    Vector vTmp(nc2);
    for (i=0; i<nc2; i++)
    {
        if (lambda[i]!=0.0)
        {
            b[k]=b[ii[i]];
            k++;
        }
    }
    vBO.setSize(k);
    vBO.permutIn(vTmp,viPermut_QP);
    mR_QP.solveInPlace(vTmp);
    mQ_QP.multiply(vP,vTmp);
}
Esempio n. 11
0
std::string		World::serialize(const Vector2i &chunkId)
{
  ProtocolMessage	msg;
  ChunkData		*chunkData = new ChunkData;
  VectorInt		*vecInt;
  std::string		serialized;
  Chunk			*chunk;
  unsigned int		fgcont = 0;
  unsigned int		bgcont = 0;
  TileType		fgtile;
  TileType		bgtile;
  TileType		oldfgtile;
  TileType		oldbgtile;

  if ((chunk = getChunk(chunkId)) != nullptr)
    {
      for (unsigned int y = 0; y < Chunk::height; ++y)
	{
	  for (unsigned int x = 0; x < Chunk::width; ++x)
	    {
	      fgtile = chunk->getTile(x, y);
	      bgtile = chunk->getBgTile(x, y);
	      if (x == 0 && y == 0)
		{
		  oldfgtile = fgtile;
		  oldbgtile = bgtile;
		}
	      else
		{
		  if (fgtile != oldfgtile)
		    {
		      chunkData->add_fgnumber(fgcont);
		      chunkData->add_fgtilecode(static_cast<unsigned int>(oldfgtile));
		      fgcont = 0;
		      oldfgtile = fgtile;
		    }
		  if (bgtile != oldbgtile)
		    {
		      chunkData->add_bgnumber(bgcont);
		      chunkData->add_bgtilecode(static_cast<unsigned int>(oldbgtile));
		      bgcont = 0;
		      oldbgtile = bgtile;
		    }
		}
	      ++fgcont;
	      ++bgcont;
	    }
	}
    }
  chunkData->add_bgnumber(bgcont);
  chunkData->add_bgtilecode(static_cast<unsigned int>(oldbgtile));
  chunkData->add_fgnumber(fgcont);
  chunkData->add_fgtilecode(static_cast<unsigned int>(oldfgtile));
  vecInt = new VectorInt;
  vecInt->set_x(chunkId.x);
  vecInt->set_y(chunkId.y);
  chunkData->set_allocated_id(vecInt);
  msg.set_content(ProtocolMessage::CHUNK);
  msg.set_allocated_chunkdata(chunkData);
  msg.SerializeToString(&serialized);
  return serialized;
}
Esempio n. 12
0
RasterPtr  SegmentorOTSU::SegmentImage (RasterPtr  srcImage,
                                        kkint32    numClasses,
                                        double&    sep
                                       )
{
  /*
  function [IDX,sep] = otsu (srcImage, numClasses)

  %OTSU Global image thresholding/segmentation using Otsu's method.
  %   IDX = OTSU(srcImage,N) segments the image srcImage into N classes by means of Otsu's
  %   N-thresholding method. OTSU returns an array IDX containing the cluster
  %   indexes (from 1 to N) of each point. Zero values are assigned to
  %   non-finite (NaN or Inf) pixels.
  %
  %   IDX = OTSU(srcImage) uses two classes (N=2, default value).
  %
  %   [IDX,sep] = OTSU(...) also returns the value (sep) of the separability
  %   criterion within the range [0 1]. Zero is obtained only with data
  %   having less than N values, whereas one (optimal value) is obtained only
  %   with N-valued arrays.
  %
  %   Notes:
  %   -----
  %   It should be noticed that the thresholds generally become less credible
  %   as the number of classes (N) to be separated increases (see Otsu's
  %   paper for more details).
  %
  %   If srcImage is an RGB image, a Karhunen-Loeve transform is first performed on
  %   the three R,G,B channels. The segmentation is then carried out on the
  %   image component that contains most of the energy. 
  %
  %   Example:
  %   -------
  %   load clown
  %   subplot(221)
  %   X = ind2rgb(X,map);
  %   imshow(X)
  %   title('Original','FontWeight','bold')
  %   for numClasses = 2:4
  %     IDX = otsu(X,numClasses);
  %     subplot(2,2,numClasses)
  %     imagesc(IDX), axis image off
  %     title(['numClasses = ' int2str(numClasses)],'FontWeight','bold')
  %   end
  %   colormap(gray)
  %
  %   Reference:
  %   ---------
  %   Otsu N, <a href="matlab:web('http://dx.doi.org/doi:10.1109/TSMC.1979.4310076')">A Threshold Selection Method from Gray-Level Histograms</a>,
  %   IEEE Trans. Syst. Man Cybern. 9:62-66;1979 
  %
  %   See also GRAYTHRESH, IM2BW
  %
  %   -- Damien Garcia -- 2007/08, revised 2010/03
  %   Visit my <a
  %   href="matlab:web('http://www.biomecardio.com/matlab/otsu.html')">website</a> for more details about OTSU
  */
  
  kkint32  pixelIdx = 0;
  kkint32  x        = 0;
  bool  isColorImage = srcImage->Color ();

  //  Checking numClasses (number of classes)
  
  if  (numClasses == 1)
  {
    //IDX = NaN(size(srcImage));
    //sep = 0;
    return  NULL;
  }

  else if  ((numClasses < 1)  ||  (numClasses > 255))
  {
    log.Level (-1) << "SegmentorOTSU::SegmentImage  ***ERROR***   'numClasses must be a between 1 and 255 !'" << endl;
    sep = 0;
    return NULL;
  }

  if  (isColorImage)
  {
    srcImage = srcImage->CreateGrayScaleKLT ();
  }
  else
  {
    srcImage = new Raster (*srcImage);
  }

  kkint32  totPixels = srcImage->TotPixels ();
  kkint32  pixelsCounted = 0;
  VectorInt  unI;
  VectorInt  unICounts;
  VectorInt32  counts (256, 0);
  {
    // %% Convert to 256 levels
    // srcImage = srcImage-min(srcImage(:));
    // srcImage = round(srcImage/max(srcImage(:))*255);
    //  Re-scale Source Image to utilize range of 0 through 255.

    //%% Probability dCistribution
    //unI = sort(unique(srcImage));
    //nbins = min(length(unI),256);
 

    uchar*  greenArea = srcImage->GreenArea ();

    uchar  pixelMin = 255;
    uchar  pixelMax = 1;

    for  (pixelIdx = 1;  pixelIdx < totPixels;  ++pixelIdx)
    {
      if  (greenArea[pixelIdx] < 1)
        continue;

      pixelsCounted++;

      if  (greenArea[pixelIdx] < pixelMin)
        pixelMin = greenArea[pixelIdx];

      if  (greenArea[pixelIdx] > pixelMax)
        pixelMax = greenArea[pixelIdx];
    }

    VectorInt  counts (256, 0);

    for  (pixelIdx = 0;  pixelIdx < totPixels;  ++pixelIdx)
    {
      /*
      double  pixelFraction = (double)((double)(greenArea[pixelIdx]) - pixelMin) / (double)srcRange;
      kkuint32  newPixelVal = (uchar)(pixelFraction * 256.0 + 0.5);
      if  (newPixelVal > 255)
        newPixelVal = 255;

      greenArea[pixelIdx] = (uchar)newPixelVal;
      counts[newPixelVal]++;
      */
      counts[greenArea[pixelIdx]]++;
    }

    for  (x = 1;  x < (kkint32)counts.size ();  ++x)
    {
      if  (counts[x] > 0)
      {
        unI.push_back (x);
        unICounts.push_back (counts[x]);
      }
    }
  }

  kkint32  nbins = (kkint32)unI.size ();

  if  (nbins <= numClasses)
  {
    // IDX = ones (size(srcImage));
    //for i = 1:numClasses, IDX(srcImage==unI(i)) = i; end
    //sep = 1;
    RasterPtr  result = new Raster (srcImage->Height (), srcImage->Width (), false);
    for  (x = 0;  x < nbins;  ++x)
    {
      LabelRaster (result, unI[x], x, srcImage);
    }
    sep = 1;
    delete  srcImage;   
    srcImage = NULL;
    return  result;
  }

  //elseif  (nbins < 256)
  //  [histo,pixval] = hist(srcImage(:),unI);
  //else
  //  [histo,pixval] = hist(srcImage(:),256);
  VectorInt  histo  = unICounts;
  VectorInt  pixval = unI;

  //P = histo/sum(histo);
  VectorDouble  P (histo.size (), 0.0);
  for  (x = 0;  x < (kkint32)histo.size ();  ++x)
    P[x] = (double)(histo[x]) / (double)pixelsCounted;

  //clear unI
  unI.clear ();

  //%% Zeroth- and first-order cumulative moments
  //w = cumsum(P);
  VectorDouble  w (P.size (), 0.0);
  w[0] = P[0];
  for  (x = 1;  x < (kkint32)P.size (); ++x)
    w[x] = w[x - 1] + P[x];

  //mu = cumsum((1:nbins).*P);
  VectorDouble  mu (P.size (), 0.0);
  mu[0] = 1.0 * P[0];
  for  (x = 1;  x < (kkint32)P.size ();  ++x)
    mu[x] = mu[x - 1] + ((x + 1) * P[x]);
  double  muEnd = mu[mu.size () - 1];
  
  //%% Maximal sigmaB^2 and Segmented image
  if  (numClasses == 2)
  {
    //sigma2B =...
    //    (mu(end) * w(2:end-1) - mu(2:end-1)) .^2  ./  w(2:end-1)./(1-w(2:end-1));
    //    ------------------- P1 -----------------      ----------- P2 -----------
    //[maxsig,k] = max(sigma2B);

    VectorDouble  wSubSet  = SubSet (w,  1, (kkint32)w.size  () - 2);
    VectorDouble  muSubSet = SubSet (mu, 1, (kkint32)mu.size () - 2);
   
    VectorDouble P1 = Power (Subt (muEnd * wSubSet, muSubSet), 2.0);
    VectorDouble P2 = DotDiv (wSubSet, Subt (1.0, wSubSet));
    VectorDouble sigma2B = DotDiv (P1, P2);
    double  maxSig = sigma2B[0];
    kkint32 maxSigIdx = 0;
    for  (x = 1;  x < (kkint32)sigma2B.size ();  ++x)
    {
      if  (sigma2B[x] > maxSig)
      {
        maxSig = sigma2B[x];
        maxSigIdx = x;
      }
    }
      
    //[maxsig,k] = max(sigma2B);
    kkint32  k = maxSigIdx;
    
    //% segmented image
    //IDX = ones(size(srcImage));
    //IDX(srcImage>pixval(k+1)) = 2;
    threshold1 = pixval[k + 1];
    RasterPtr  result = new Raster (srcImage->Height (), srcImage->Width (), false);
    uchar*  resultArea = result->GreenArea ();
    uchar*  srcArea    = srcImage->GreenArea ();

    while  (true)
    {
      kkuint32  numClass2Pixs = 0;
      for  (x = 0;  x < totPixels;  ++x)
      {
        if  (srcArea[x] > threshold1)
        {
          resultArea[x] = 2;
          ++numClass2Pixs;
        }
        else
        {
          resultArea[x] = 1;
        }
      }

      if  ((threshold1 < 1)  ||  (numClass2Pixs >100))
        break;
      --threshold1;
    }
    
    //% separability criterion
    //sep = maxsig/sum(((1:nbins)-mu(end)).^2.*P);
    double  sum = 0.0;
    kkint32  y = 0;
    muEnd = mu[mu.size () - 1];
    for  (x = 0, y = 1;  x < nbins;  ++x, ++y)
      sum = pow (((double)y - muEnd), 2.0) * P[x];

    sep = maxSig / sum;
    delete  srcImage;
    srcImage = NULL;
    return  result;
  }
    
  if  (numClasses == 3)
  {
    //w0 = w;
    //w2 = fliplr(cumsum(fliplr(P)));
    VectorDouble  w0 = w;
    VectorDouble  w2 = FlipLeftRight (CumSum (FlipLeftRight (P)));


    //[w0,w2] = ndgrid(w0,w2);
    Matrix w0M ((kkint32)w0.size (), (kkint32)w0.size ());
    Matrix w2M ((kkint32)w2.size (), (kkint32)w2.size ());
    NdGrid (w0, w2, w0M, w2M);

    
    //mu0 = mu./w;
    VectorDouble  mu0 = DotDiv (mu, w);

    //mu2 = fliplr(cumsum(fliplr((1:nbins).*P)) ./ cumsum(fliplr(P)));
    //            1      2      34       4   32        3      4 321
    //             ---------- P1 -------------     ------ P2 --------
    VectorDouble  P1 = CumSum (FlipLeftRight (DotMult (BDV (1.0, 1.0, (double)nbins), P)));
    VectorDouble  P2 = CumSum (FlipLeftRight (P));
    VectorDouble  mu2 = FlipLeftRight (DotDiv (P1, P2));

    // TODO  
    //[mu0,mu2] = ndgrid(mu0,mu2);
    Matrix  mu0M ((kkint32)mu0.size (), (kkint32)mu0.size ());
    Matrix  mu2M ((kkint32)mu2.size (), (kkint32)mu2.size ());
    NdGrid (mu0, mu2, mu0M, mu2M);
    
    //w1 = 1-w0-w2;
    Matrix  w1M = 1.0 - w0M - w2M;

    //w1(w1<=0) = NaN;
    MakeNanWhenLesOrEqualZero (w1M);

    //sigma2B =...
    //    w0.*(mu0-mu(end)).^2 + w2.*(mu2-mu(end)).^2 +...
    //    (w0.*(mu0-mu(end)) + w2.*(mu2-mu(end))).^2./w1;
    Matrix  P1M = (DotMult (w0M, Power ((mu0M - muEnd), 2.0)))  +  (DotMult (w2M, Power ((mu2M - muEnd), 2.0)));
    Matrix  P2M = DotDiv (Power ((DotMult (w0M, (mu0M - muEnd)) + DotMult (w2M, (mu2M - muEnd))), 2.0), w1M);
    Matrix  sigma2B = P1M + P2M;


    //sigma2B(isnan(sigma2B)) = 0; % zeroing if k1 >= k2
    ZeroOutNaN (sigma2B);

    //[maxsig,k] = max(sigma2B(:));         % Turns sigma2B into 1D Array then locates largest value and index.
    // [k1,k2] = ind2sub([nbins nbins],k);  % Sets k1 and k2 to the indexes for k mapped into a 2D square matrix that is (nbins x nbins)
    kkint32  k1, k2;
    double  maxsig = 0.0;
    sigma2B.FindMaxValue (maxsig, k1, k2);
   
    //% segmented image
    RasterPtr  result = new Raster (srcImage->Height (), srcImage->Width (), false);
    {
      //IDX = ones(size(srcImage))*3;
      //IDX(srcImage<=pixval(k1)) = 1;
      //IDX(srcImage>pixval(k1) & srcImage<=pixval(k2)) = 2;
      uchar*  srcData = srcImage->GreenArea ();
      uchar*  data = result->GreenArea ();
      threshold1 = pixval[k1];
      threshold2 = pixval[k2];
      for  (x = 0;  x < totPixels;  ++x)
      {
        if  (srcData[x] <= threshold1)
          data[x] = 1;
        else if  (srcData[x] <= threshold2)
          data[x] = 2;
        else
          data[x] = 3;
      }
    }
    
    //% separability criterion
    //sep = maxsig / sum (((1:nbins)-mu(end)).^2.*P);

    //VectorDouble  xxx = BDV (1.0, 1.0, (double)nbins);
    //VectorDouble  yyy = Subt (xxx, muEnd);
    //VectorDouble  zzz = Power (yyy, 2.0);
    sep = maxsig / Sum (DotMult (Power (Subt (BDV (1.0, 1.0, (double)nbins), muEnd), 2.0), P));
    delete  srcImage;
    srcImage = NULL;
    return  result;
  }
    
  {
    /*
    //k0 = linspace(0,1,numClasses+1);   %  k0 = row vector of linear spaced points between 0 and 1  with (numClasses + 1) points
    VectorDouble  k0 = LinSpace (0, 1, numClasses + 1);

    //k0 = k0(2:numClasses);
    

    [k,y] = fminsearch(@sig_func,k0,optimset('TolX',1));
    k = round(k*(nbins-1)+1);
    
    % segmented image
    IDX = ones(size(srcImage))*numClasses;
    IDX(srcImage<=pixval(k(1))) = 1;
    for i = 1:numClasses-2
        IDX(srcImage>pixval(k(i)) & srcImage<=pixval(k(i+1))) = i+1;
    end
    
    % separability criterion
    sep = 1-y;
    */
  }

  delete  srcImage;
  srcImage = NULL;
    
  return NULL;
}  /* SegmentImage */
Esempio n. 13
0
/**
 *@brief  Segments image into 'numClasses' taking into account only pixels 
 *        indicated by 'mask' image.
 *@param[in]  srcImage  Image to segment.  If it is a color image will be 
 *                      converted to GrayScale using 'CreateGrayScaleKLTOnMaskedArea'
 *@param[in]  mask  Indicates which pixels to consider when thresholding image.  Pixels 
 *                  that are not part of mask will be assigned label '0'.
 *@param[in]  numClasses Number of classes to segment image into.  Current only '2' and '3' are supported.
 *@param[out]  sep  
 *@return  Labeled GrayScale image where pixels will be label into their respective class; between '1' and 'numClasses'.
 */
RasterPtr  SegmentorOTSU::SegmentMaskedImage (RasterPtr  srcImage,
                                              RasterPtr  mask,
                                              kkint32    numClasses,
                                              double&    sep
                                             )
{
  kkint32  pixelIdx = 0;
  kkint32  x        = 0;
  bool  isColorImage = srcImage->Color ();

  uchar*  maskArea = NULL;
  uchar   maskTh   = 0;
  if  (mask)
  {
    maskArea = mask->GreenArea ();
    maskTh   = mask->BackgroundPixelTH ();
  }

  if  (numClasses == 1)
  {
    return  NULL;
  }

  else if  ((numClasses < 1)  ||  (numClasses > 255))
  {
    log.Level (-1) << endl << endl
      << "SegmentorOTSU::SegmentMaskedImage  ***ERROR***   'numClasses must be a between 1 and 255 !'" << endl
      << endl;
    sep = 0;
    return NULL;
  }

  if  (isColorImage)
  {
    if  (mask)
      srcImage = srcImage->CreateGrayScaleKLTOnMaskedArea (*mask);
    else
      srcImage = srcImage->CreateGrayScaleKLT ();
  }
  else
  {
    srcImage = new Raster (*srcImage);
  }

  kkint32  totPixels = srcImage->TotPixels ();
  kkint32  totMaskPixels = totPixels;
  if  (mask)
    totMaskPixels = mask->TotalBackgroundPixels ();

  VectorInt  unI;
  VectorInt  unICounts;
  
  {
    uchar*  greenArea = srcImage->GreenArea ();

    uchar  pixelMin = greenArea[0];
    uchar  pixelMax = greenArea[0];

    for  (pixelIdx = 1;  pixelIdx < totPixels;  ++pixelIdx)
    {
      if  ((!mask)  ||  (maskArea[pixelIdx] > maskTh))
      {
        if  (greenArea[pixelIdx] < pixelMin)
          pixelMin = greenArea[pixelIdx];

        if  (greenArea[pixelIdx] > pixelMax)
          pixelMax = greenArea[pixelIdx];
      }
    }

    //kkint32  srcRange = pixelMax - pixelMin + 1;
    VectorInt  counts (256, 0);

    for  (pixelIdx = 0;  pixelIdx < totPixels;  ++pixelIdx)
    {
      if  ((!mask)  ||  (maskArea[pixelIdx] > maskTh))
        counts[greenArea[pixelIdx]]++;
    }

    for  (x = 0;  x < (kkint32)counts.size ();  ++x)
    {
      if  (counts[x] > 0)
      {
        unI.push_back (x);
        unICounts.push_back (counts[x]);
      }
    }
  }

  kkint32  nbins = (kkint32)unI.size ();

  if  (nbins <= numClasses)
  {
    RasterPtr  result = new Raster (srcImage->Height (), srcImage->Width (), false);
    for  (x = 0;  x < nbins;  ++x)
    {
      LabelRaster (result, mask, unI[x], x, srcImage);
    }
    sep = 1;
    delete  srcImage;   
    srcImage = NULL;
    return  result;
  }

  VectorInt  histo  = unICounts;
  VectorInt  pixval = unI;

  VectorDouble  P (histo.size (), 0.0);
  for  (x = 0;  x < (kkint32)histo.size ();  ++x)
    P[x] = (double)(histo[x]) / (double)totMaskPixels;

  unI.clear ();

  //%% Zeroth- and first-order cumulative moments
  //w = cumsum(P);
  VectorDouble  w (P.size (), 0.0);
  w[0] = P[0];
  for  (x = 1;  x < (kkint32)P.size (); ++x)
    w[x] = w[x - 1] + P[x];

  //mu = cumsum((1:nbins).*P);
  VectorDouble  mu (P.size (), 0.0);
  mu[0] = 1.0 * P[0];
  for  (x = 1;  x < (kkint32)P.size ();  ++x)
    mu[x] = mu[x - 1] + ((x + 1) * P[x]);
  double  muEnd = mu[mu.size () - 1];
  
  //%% Maximal sigmaB^2 and Segmented image
  if  (numClasses == 2)
  {
    //sigma2B =...
    //    (mu(end) * w(2:end-1) - mu(2:end-1)) .^2  ./  w(2:end-1)./(1-w(2:end-1));
    //    ------------------- P1 -----------------      ----------- P2 -----------
    //[maxsig,k] = max(sigma2B);

    VectorDouble  wSubSet  = SubSet (w,  1, (kkint32)w.size  () - 2);
    VectorDouble  muSubSet = SubSet (mu, 1, (kkint32)mu.size () - 2);
   
    VectorDouble P1 = Power (Subt (muEnd * wSubSet, muSubSet), 2.0);
    VectorDouble P2 = DotDiv (wSubSet, Subt (1.0, wSubSet));
    VectorDouble sigma2B = DotDiv (P1, P2);
    double  maxSig = sigma2B[0];
    kkint32 maxSigIdx = 0;
    for  (x = 1;  x < (kkint32)sigma2B.size ();  ++x)
    {
      if  (sigma2B[x] > maxSig)
      {
        maxSig = sigma2B[x];
        maxSigIdx = x;
      }
    }
      
    //[maxsig,k] = max(sigma2B);
    kkint32  k = maxSigIdx;
    
    //% segmented image
    //IDX = ones(size(srcImage));
    //IDX(srcImage>pixval(k+1)) = 2;
    kkint32  threshold = pixval[k + 1];
    RasterPtr  result = new Raster (srcImage->Height (), srcImage->Width (), false);
    uchar*  resultArea = result->GreenArea ();
    uchar*  srcArea    = srcImage->GreenArea ();
    for  (x = 0;  x < totPixels;  ++x)
    {
      if  ((!maskArea)  ||  (maskArea[x] > maskTh))
      {
        if  (srcArea[x] > threshold)
          resultArea[x] = 2;
        else
          resultArea[x] = 1;
      }
      else
      {
        resultArea[x] = 0;
      }
    }
    
    //% separability criterion
    //sep = maxsig/sum(((1:nbins)-mu(end)).^2.*P);
    double  sum = 0.0;
    kkint32  y = 0;
    muEnd = mu[mu.size () - 1];
    for  (x = 0, y = 1;  x < nbins;  ++x, ++y)
      sum = pow (((double)y - muEnd), 2.0) * P[x];

    sep = maxSig / sum;
    delete  srcImage;
    srcImage = NULL;
    return  result;
  }
    
  if  (numClasses == 3)
  {
    VectorDouble  w0 = w;
    VectorDouble  w2 = FlipLeftRight (CumSum (FlipLeftRight (P)));

    Matrix w0M ((kkint32)w0.size (), (kkint32)w0.size ());
    Matrix w2M ((kkint32)w2.size (), (kkint32)w2.size ());
    NdGrid (w0, w2, w0M, w2M);
    
    VectorDouble  mu0 = DotDiv (mu, w);

    //mu2 = fliplr(cumsum(fliplr((1:nbins).*P)) ./ cumsum(fliplr(P)));
    //            1      2      34       4   32        3      4 321
    //             ---------- P1 -------------     ------ P2 --------
    VectorDouble  P1 = CumSum (FlipLeftRight (DotMult (BDV (1.0, 1.0, (double)nbins), P)));
    VectorDouble  P2 = CumSum (FlipLeftRight (P));
    VectorDouble  mu2 = FlipLeftRight (DotDiv (P1, P2));

    //[mu0,mu2] = ndgrid(mu0,mu2);
    Matrix  mu0M ((kkint32)mu0.size (), (kkint32)mu0.size ());
    Matrix  mu2M ((kkint32)mu2.size (), (kkint32)mu2.size ());
    NdGrid (mu0, mu2, mu0M, mu2M);
    
    //w1 = 1-w0-w2;
    Matrix  w1M = 1.0 - w0M - w2M;

    //w1(w1<=0) = NaN;
    MakeNanWhenLesOrEqualZero (w1M);

    //sigma2B =...
    //    w0.*(mu0-mu(end)).^2 + w2.*(mu2-mu(end)).^2 +...
    //    (w0.*(mu0-mu(end)) + w2.*(mu2-mu(end))).^2./w1;
    Matrix  P1M = (DotMult (w0M, Power ((mu0M - muEnd), 2.0)))  + (DotMult (w2M, Power ((mu2M - muEnd), 2.0)));
    Matrix  P2M = DotDiv (Power ((DotMult (w0M, (mu0M - muEnd)) +  DotMult (w2M, (mu2M - muEnd))), 2.0), w1M);
    Matrix  sigma2B = P1M + P2M;

    //sigma2B(isnan(sigma2B)) = 0; % zeroing if k1 >= k2
    ZeroOutNaN (sigma2B);

    //[maxsig,k] = max(sigma2B(:));         % Turns sigma2B into 1D Array then locates largest value and index.
    // [k1,k2] = ind2sub([nbins nbins],k);  % Sets k1 and k2 to the indexes for k mapped into a 2D square matrix that is (nbins x nbins)
    kkint32  k1, k2;
    double  maxsig = 0.0;
    sigma2B.FindMaxValue (maxsig, k1, k2);
   
    //% segmented image
    RasterPtr  result = new Raster (srcImage->Height (), srcImage->Width (), false);
    {
      //IDX = ones(size(srcImage))*3;
      //IDX(srcImage<=pixval(k1)) = 1;
      //IDX(srcImage>pixval(k1) & srcImage<=pixval(k2)) = 2;
      uchar*  srcData = srcImage->GreenArea ();
      uchar*  data = result->GreenArea ();
      double  th1 = pixval[k1];
      double  th2 = pixval[k2];
      for  (x = 0;  x < totPixels;  ++x)
      {
        if  ((!maskArea)  ||  (maskArea[x] > maskTh))
        {
          if  (srcData[x] <= th1)
            data[x] = 1;
          else if  (srcData[x] <= th2)
            data[x] = 2;
          else
            data[x] = 3;
        }
        else
        {
          data[x] = 0;
        }
      }
    }
    
    sep = maxsig / Sum (DotMult (Power (Subt (BDV (1.0, 1.0, (double)nbins), muEnd), 2.0), P));
    delete  srcImage;
    srcImage = NULL;
    return  result;
  }
    
  delete  srcImage;
  srcImage = NULL;
    
  return NULL;
}  /* SegmentMaskedImage */
Esempio n. 14
0
void  ClassSummaryList::SaveLLoydsBinsData (const KKStr&  fileName,
                                            const KKStr&  srcDirName,
                                            kkint32       lastScanLine,
                                            kkint32         baseLLoydsBinSize
                                           )
{
  ofstream o (fileName.Str (), ios::out);
  if  (!o.is_open ())
  {
    log.Level (-1) << endl << endl << endl
                   << "ClassSummaryList::SaveLLoydsBinsData       *** Invalid File[" << fileName << "]."  << endl
                   << endl;
    return;
  }
  
  ClassSummaryList::const_iterator  idx;

  o << "//  LLoyds Bins  Data"                              << endl
    << "//"                                                 << endl
    << "// Run Date      [" << osGetLocalDateTime () << "]"   << endl
    << "// SrcDir        [" << srcDirName            << "]"   << endl
    << "// LastScanLin   [" << lastScanLine          << "]"   << endl
    << "// Base Bin Size [" << baseLLoydsBinSize     << "]"   << endl
    << "//"                                                 << endl;

  o << "BinSize" << "\t" << "BinNum" << "\t" << "ScanLines";
  kkuint32  numOfBins = NumOfLLoydsBins ();
  for  (idx = begin ();  idx != end ();  idx++)
  {
    ClassSummaryPtr  cs = *idx;
    o << "\t" << cs->ClassName ();
  }
  o << endl;

  VectorInt  binSizes = LLoydsBinSizes ();
  size_t  binSizeIndex = 0;
  for  (binSizeIndex = 0;  binSizeIndex < binSizes.size ();  binSizeIndex++)
  {
    kkint32  binSize = binSizes[binSizeIndex];

    kkint32 startScanLinNum = 0;
    kkint32 endScanLineNum  = startScanLinNum + binSize - 1;

    kkuint32  binNum = 0;
    for  (binNum = 0;  binNum < numOfBins;  binNum++)
    {
      o << binSize << "\t" << binNum <<"\t" << startScanLinNum << "-" << endScanLineNum;

      for  (idx = begin ();  idx != end ();  idx++)
      {
        kkint32  lloydsBin = 0;
        ClassSummaryPtr  cs = *idx;
        LLoydsEntryPtr  lloydsEntry = cs->LLoydsEntryByBinSize (binSize);
        if  (lloydsEntry != NULL)
          lloydsBin = lloydsEntry->LLoydsBin (binNum);
        o << "\t" << lloydsBin;
      }
      startScanLinNum += binSize;
      endScanLineNum  += binSize;
      o << endl;
    }

  }

  o.close ();
}  /* SaveLLoydsBinsData */
Esempio n. 15
0
void simpleQPSolve(Matrix mH, Vector vG, Matrix mA, Vector vB,   // in
                   Vector vP, Vector vLambda, int *info)         // out
{
    const double tolRelFeasibility=1e-6;
//     int *info=NULL;
    int dim=mA.nColumn(), nc=mA.nLine(), ncr, i,j,k, lastJ=-2, *ii;
    MatrixTriangle M(dim);
    Matrix mAR, mZ(dim,dim-1), mHZ(dim,dim-1), mZHZ(dim-1,dim-1);
    Vector vTmp(mmax(nc,dim)), vYB(dim), vD(dim), vTmp2(dim), vTmp3(nc), vLast(dim), 
           vBR_QP, vLambdaScale(nc);
    VectorChar vLB(nc);
    double *lambda=vLambda, *br, *b=vB, violationMax, violationMax2,
           *rlambda,ax,al,dviolation, **a=mA, **ar=mAR, mymin, mymax, maxb, *llambda,
           **r,t, *scaleLambda=vLambdaScale;
    char finished=0, feasible=0, *lb=vLB;

    if (info) *info=0;

    // remove lines which are null
    k=0; vi_QP.setSize(nc); maxb=0.0;
    for (i=0; i<nc; i++)
    {
        mymin=INF; mymax=-INF;
        for (j=0; j<dim; j++)
        {
            mymin=mmin(mymin,a[i][j]);
            mymax=mmax(mymax,a[i][j]);
            if ((mymin!=mymax)||(mymin!=0.0)||(mymax!=0.0)) break;
        }
        if ((mymin!=mymax)||(mymin!=0.0)||(mymax!=0.0))
        {
            lambda[k]=lambda[i];
            maxb=mmax(maxb,condorAbs(b[i]));
            scaleLambda[k]=mA.euclidianNorm(i);
            vi_QP[k]=i;
            k++;
        }
    }
    nc=k; vi_QP.setSize(nc); ii=vi_QP; maxb=(1.0+maxb)*tolRelFeasibility;
    vLast.zero(); 
    
    for (i=0; i<nc; i++) if (lambda[i]!=0.0) lb[i]=2; else lb[i]=1;

    while (!finished)
    {
        finished=1;
        mAR.setSize(dim,dim); mAR.zero(); ar=mAR;
        vBR_QP.setSize(mmin(nc,dim)); br=vBR_QP;
        ncr=0;
        for (i=0; i<nc; i++)
            if (lambda[i]!=0.0)
            {
//                mAR.setLines(ncr,mA,ii[i],1);
                k=ii[i];
                t=scaleLambda[ncr];
                for (j=0; j<dim; j++) ar[ncr][j]=a[k][j]*t;
                br[ncr]=b[ii[i]]*t;
                ncr++;
            }
        mAR.setSize(ncr,dim);
        vBR_QP.setSize(ncr);
        vLastLambda_QP.copyFrom(vLambda); llambda=vLastLambda_QP;

        if (ncr==0)
        {
            // compute step
            vYB.copyFrom(vG);
            vYB.multiply(-1.0);
            if (mH.cholesky(M))
            {
                M.solveInPlace(vYB);
                M.solveTransposInPlace(vYB);
            } else
            {
                printf("warning: cholesky factorisation failed.\n");
                if (info) *info=2;
            }
            vLambda.zero();
        } else
        {
            Matrix mAR2=mAR.clone(), mQ2;
            MatrixTriangle mR2;
            mAR2.QR(mQ2,mR2);

            mAR.QR(mQ_QP,mR_QP, viPermut_QP); // content of mAR is destroyed here !
            bQRFailed_QP=0;

            r=mR_QP;
            for (i=0; i<ncr; i++)
                if (r[i][i]==0.0)
                {
                    // one constraint has been wrongly added.
                    bQRFailed_QP=1;
                    QPReconstructLambda(vLambda,vLambdaScale); vP.copyFrom(vLast); return; 
                }

            for (i=0; i<ncr; i++)
                if (viPermut_QP[i]!=i)
                {
                  //  printf("whoups.\n");
                }
            if (ncr<dim)
            {
                mQ_QP.getSubMatrix(mZ,0,ncr);

                // Z^t H Z
                mH.multiply(mHZ,mZ);
                mZ.transposeAndMultiply(mZHZ,mHZ);
                mQ_QP.setSize(dim,ncr);            
            }

            // form Yb
            vBR_QP.permutIn(vTmp,viPermut_QP);
            mR_QP.solveInPlace(vTmp);
            mQ_QP.multiply(vYB,vTmp);

            if (ncr<dim)
            {

                // ( vG + H vYB )^t Z : result in vD
                
                mH.multiply(vTmp,vYB);
                vTmp+=vG;
                vTmp.transposeAndMultiply(vD,mZ);

                // calculate current delta (result in vD)
                vD.multiply(-1.0);
                if (mZHZ.cholesky(M))
                {
                    M.solveInPlace(vD);
                    M.solveTransposInPlace(vD);
                }
                else
                {
                    printf("warning: cholesky factorisation failed.\n");
                    if (info) *info=2;
                };

                // evaluate vX* (result in vYB):
                mZ.multiply(vTmp, vD);
                vYB+=vTmp;
            }

            // evaluate vG* (result in vTmp2)
            mH.multiply(vTmp2,vYB);
            vTmp2+=vG;

            // evaluate lambda star (result in vTmp):
            mQ2.transposeAndMultiply(vTmp,vTmp2);
            mR2.solveTransposInPlace(vTmp);

            // evaluate lambda star (result in vTmp):
            mQ_QP.transposeAndMultiply(vTmp3,vTmp2);
            mR_QP.solveTransposInPlace(vTmp3);
            vTmp3.permutOut(vTmp,viPermut_QP);
            rlambda=vTmp;

            ncr=0;
            for (i=0; i<nc; i++)
                if (lambda[i]!=0.0)
                {
                    lambda[i]=rlambda[ncr];
                    ncr++;
                }
        } // end of test on ncr==0

        // find the most violated constraint j among non-active Linear constraints:
        j=-1;
        if (nc>0)
        {
            k=-1; violationMax=-INF; violationMax2=-INF;
            for (i=0; i<nc; i++)
            {
                if (lambda[i]<=0.0) // test to see if this constraint is not active 
                {
                    ax=mA.scalarProduct(ii[i],vYB);
                    dviolation=b[ii[i]]-ax;
                    if (llambda[i]==0.0)
                    {
                        // the constraint was not active this round
                        // thus, it can enter the competition for the next 
                        // active constraint

                        if (dviolation>maxb)
                        {
                            // the constraint should be activated
                            if (dviolation>violationMax2) 
                                { k=i; violationMax2=dviolation; }
                            al=mA.scalarProduct(ii[i],vLast)-ax; 
                            if (al>0.0) // test to see if we are going closer
                            {  
                                dviolation/=al;
                                if (dviolation>violationMax ) 
                                    { j=i; violationMax =dviolation; }
                            }
                        }
                    } else
                    {
                        lb[i]--;
                        if (feasible) 
                        {
                            if (lb[i]==0) 
                            {
                                vLambda.copyFrom(vLastLambda_QP);
                                if (lastJ>=0) lambda[lastJ]=0.0;
                                QPReconstructLambda(vLambda,vLambdaScale); 
                                vP.copyFrom(vYB); 
                                return; 
                            }
                        } else
                        {
                            if (lb[i]==0)
                            {
                                if (info) *info=1;
                                QPReconstructLambda(vLambda,vLambdaScale); 
                                vP.zero(); 
                                return;
                            }
                        }
                        finished=0;  // this constraint was wrongly activated.
                        lambda[i]=0.0;
                    }
                }
            }

            // !!! the order the tests is important here !!!
            if ((j==-1)&&(!feasible)) 
            { 
                feasible=1; 
                for (i=0; i<nc; i++) if (llambda[i]!=0.0) lb[i]=2; else lb[i]=1;
            }
            if (j==-1) { j=k; violationMax=violationMax2; } // change j to k after feasible is set
            if (ncr==mmin(dim,nc)) { 
                if (feasible) { // feasible must have been checked before
                    QPReconstructLambda(vLambda,vLambdaScale); vP.copyFrom(vYB); return; 
                } else
                {
                    if (info) *info=1;
                    QPReconstructLambda(vLambda,vLambdaScale); vP.zero(); return; 
                }
            }
            // activation of constraint only if ncr<mmin(dim,nc)
            if (j>=0) { lambda[j]=1e-5; finished=0; } // we need to activate a new constraint 
//            else if (ncr==dim){ 
//                QPReconstructLambda(vLambda); vP.copyFrom(vYB); return; }
        }

        // to prevent rounding error
        if (j==lastJ) { 
//        if (0) {
            QPReconstructLambda(vLambda,vLambdaScale); vP.copyFrom(vYB); return; }
        lastJ=j;

        vLast.copyFrom(vYB);
    }
    QPReconstructLambda(vLambda,vLambdaScale); vP.copyFrom(vYB); return;
}