Ask Your Question
0

Is it possible to create distinct Histogram bins from array

asked 2015-07-24 08:47:12 -0500

albertJ gravatar image

Hi i'm currently trying to match a large set of values with a template array. I was looking to just display any of the values which perfectly matched the array in a frequency histogram.

I've tried this so far with the cv:calcHist function using non-uniform bins and an input array roughly dividing the values into bins but was hoping there was a better way.

Such as where you can designate the upper and lower bounds for all the bins as opposed to just the first bin, is this possible? or are there any other methods, outside of prefiltering values as the template values will likely change and taking care of this in a single histogram function would make things easier.

Thanks in advance.

edit retag flag offensive close merge delete

Comments

I am not really sure that I have well understood "upper and lower bounds for all the bins", but isn't normalise going to do it?

thdrksdfthmn gravatar imagethdrksdfthmn ( 2015-07-24 09:13:17 -0500 )edit

yeah i think something like that but being able to assign a collection of values to their nearest value in a seperate array.

Is that possible with the mask parameter in normalize is?

albertJ gravatar imagealbertJ ( 2015-07-24 11:01:00 -0500 )edit

Yes, it should be possible

thdrksdfthmn gravatar imagethdrksdfthmn ( 2015-07-27 02:38:00 -0500 )edit

1 answer

Sort by ยป oldest newest most voted
1

answered 2015-09-02 05:31:06 -0500

albertJ gravatar image

for anyone looking at this, the solution i ultimately used, was just to use the non uniform bins input in the calcHist function. First i looked through and matched the input values to the nearest stored value.

    void textonFind(Mat& clus, Mat dictionary){
      if(clus.empty() || dictionary.empty()){
        ERR("Texton Find inputs were empty.");
        exit(-1);
      }
      // Loop through input centers
      for(int h=0;h<clus.rows;h++){
        float distance = 0.0, nearest = 0.0;

        distance = abs(dictionary.at<float>(0,0) - clus.at<float>(h,0));
        nearest = dictionary.at<float>(0,0);

        // Compare current centre with all values in texton dictionary
        for(int k = 0; k < dictionary.rows; k++){
          if(abs(dictionary.at<float>(k,0) - clus.at<float>(h,0)) < distance){
            nearest = dictionary.at<float>(k,0);
            distance = abs(dictionary.at<float>(k,0) - clus.at<float>(h,0));
          }
        }
        // Replace input Center with closest Texton Center
        clus.at<float>(h,0) = nearest;
      }
    }

Then to generate the bin ranges i looped through the original values i wanted to match the new values to and simply added 0.00001 this acted as the upper exclusion limit putting any values which were above this in the next bin, as i knew all the possible values i didn't need to find the nearest as that was already done.

    // Create bins for each textonDictionary Value
    void binLimits(vector<float>& tex){
      dicDEBUG("inside binLimits", 0);
      vector<float> bins;
      bins.push_back(0);
      for(int i = 0;i <= tex.size()-1;i++){
          bins.push_back(tex[i] + 0.00001);
      }
      bins.push_back(256);
      for(int i=0;i<bins.size();i++)
        cout << "texDict: " << i << ": "<< tex[i] << " becomes: " << bins[i+1] << endl;
      tex.clear();
      tex = bins;
    }

The above code isn't necessarily pretty but it works in case anyone has a similar problem.

edit flag offensive delete link more

Question Tools

1 follower

Stats

Asked: 2015-07-24 08:47:12 -0500

Seen: 288 times

Last updated: Sep 02 '15