5
$\begingroup$

For example I have 100 values sample. I'd like to build histogram in which every bin contains, for example, 10 values. How can i do that? Thanks.

$\endgroup$
8
$\begingroup$

You can use the values of the quantiles of your sample as bin delimiters for your histogram. You can think of $n$-quantiles as those threshold values that divide your data set into $n$ equal-sized subsets.

Let's generate some sample data and set your requirements, i.e. number of points per bin:

SeedRandom[10]
sample = RandomVariate[NormalDistribution[], 200];
datapointsperbin = 10;
numberofbins = IntegerPart[Length[sample]/datapointsperbin];

This is what a regular histogram with evenly spaced bins would look like for that sample:

Histogram[sample]

Even binned histogram

Now we use Quantile to calculate numberofbins quantiles for your distribution, then we use those values as bin delimiters for your histogram.

Histogram[
 sample,
 {Table[Quantile[sample, i/numberofbins], {i, 1, numberofbins - 1}]}
]

unevenly binned histogram

You can see from the vertical axis of the histogram that each bin contains 10 samples, as specified by the value of datapointperbin.


Having done this, however, I still wonder why you need such a histogram. Of course, if what you needed was to calculate the intervals that would accomplish such binning, given your sample, the magic is all in the Quantile function, so you can get those values directly as well:

Table[Quantile[sample, i/numberofbins], {i, 1, numberofbins - 1}]

{-1.8614, -1.42414, -1.21859, -0.971859, -0.905122, -0.707023, -0.470983, -0.274088, -0.163548, 0.0100698, 0.122639, 0.271601, 0.383704, 0.475579, 0.608299, 0.873699, 1.03975, 1.33463, 1.81741}

$\endgroup$
  • $\begingroup$ Wow, thanks for help. One more question: how to change y-axis value from 'number of values in each bin' to 'probability density function value for each bin'? $\endgroup$ – instajke May 16 '15 at 18:02
  • 2
    $\begingroup$ Histogram can do that for you: just add "PDF" as the bin height specification, as the following: Histogram[ sample, Table[Quantile[sample, i/numberofbins], {i, 1, numberofbins - 1}]}, "PDF" ]. $\endgroup$ – MarcoB May 16 '15 at 18:16
6
$\begingroup$

You can also define a function that produces the required bin list:

ClearAll[bF]
bF[n_] := {Quantile[#, Range[# - 1]/# &[Quotient[Length@#, n]]]} &

where we used the fact that the second argument of Quantile can be a List.

data = RandomVariate[NormalDistribution[], 200];
Row[Histogram[data, bF[10][data], #, PlotLabel -> Style[#, 16, "Panel"],
    ChartElementFunction -> "GlassRectangle", ImageSize -> 400, ChartStyle -> 63] & /@
  {"PDF", "Count"}]

enter image description here

Update: With multiple datasets, we can specify the bin lengths in a number of ways.

Using the one of the data sets as the source for specifying the bin lengths, we get an interesting comparative histogram of the two data sets:

datab = RandomVariate[NormalDistribution[], {2, 200}];

Row[Histogram[datab, bF[10][First@datab], #, 
    PlotLabel -> Style[#, 16, "Panel"],
    ChartElementFunction -> "GlassRectangle", ImageSize -> 400, 
    ChartStyle -> {Red, Blue}, 
    ChartLegends -> Placed[{"data1", "data2"}, Bottom]] & /@
  {"PDF", "Count"}]

enter image description here

Row[Histogram[datab, bF[10][Last@datab], #, 
    PlotLabel -> Style[#, 16, "Panel"],
    ChartElementFunction -> "GlassRectangle", ImageSize -> 400, 
    ChartStyle -> {Red, Blue}, 
    ChartLegends -> Placed[{"data1", "data2"}, Bottom]] & /@
  {"PDF", "Count"}]

enter image description here

Specifying bin lengths based on Joined data sets, and on the Union of data sets, we get the following:

Row[Histogram[datab, bF[20][Join @@ datab], #, 
    PlotLabel -> Style[#, 16, "Panel"],
    ChartElementFunction -> "GlassRectangle", ImageSize -> 400, 
    ChartStyle -> {Red, Blue}, 
    ChartLegends -> Placed[{"data1", "data2"}, Bottom]] & /@
  {"PDF", "Count"}]

enter image description here

Row[Histogram[datab, bF[10][First@Union@datab], #, 
    PlotLabel -> Style[#, 16, "Panel"],
    ChartElementFunction -> "GlassRectangle", ImageSize -> 400, 
    ChartStyle -> {Red, Blue}, 
    ChartLegends -> Placed[{"data1", "data2"}, Bottom]] & /@
  {"PDF", "Count"}]

enter image description here

$\endgroup$
  • $\begingroup$ That's absolutely amazing. Thank You a lot. $\endgroup$ – instajke May 16 '15 at 21:01
  • $\begingroup$ @instajke, my pleasure. $\endgroup$ – kglr May 16 '15 at 21:14
  • $\begingroup$ Very nice and great idea. $\endgroup$ – Algohi May 16 '15 at 21:14
  • $\begingroup$ Thank you @Algohi. $\endgroup$ – kglr May 16 '15 at 21:19

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.