Skip to content

Instantly share code, notes, and snippets.

@paul-english
Created February 11, 2013 04:58
Show Gist options
  • Save paul-english/4752760 to your computer and use it in GitHub Desktop.
Save paul-english/4752760 to your computer and use it in GitHub Desktop.
Some work graphing a few probability distributions using d3.js
var probability = {
normal: function(x, mean, stddev) {
var y = (1 / (stddev * Math.sqrt(2 * Math.PI))) * Math.pow(Math.E, - (Math.pow(x - mean, 2) / (2 * Math.pow(stddev, 2))));
//console.log('normal', x, mean, stddev, y);
return y;
},
logNormal: function(x, mean, stddev) {
var y = (1 / (x * Math.sqrt(2 * Math.PI * Math.pow(stddev, 2)))) * Math.pow(Math.E, - (Math.pow(Math.log(x) - mean, 2) / (2 * Math.pow(stddev, 2))));
//console.log('logNormal', x, mean, stddev, y);
y = isFinite(y) ? y : 0;
return y;
},
erlang: function(x, kappa, lambda) {
var y = (Math.pow(lambda, kappa) * Math.pow(x, kappa - 1) * Math.pow(Math.E, - lambda * x)) / probability.factorial(kappa - 1);
//console.log('erlang', x, kappa, lambda, y);
return y;
},
erlangScale: function(x, kappa, scale) {
var y = (Math.pow(x, kappa - 1) * Math.pow(Math.E, - x / scale)) / (Math.pow(scale, kappa) * probability.factorial(kappa - 1));
//console.log('erlang scale', x, kappa, scale, y);
return y;
},
factorial: function(n) {
var rval=1;
for (var i = 2; i <= n; i++)
rval = rval * i;
return rval;
}
};
///////////////////////////
var graph = function(selector) {
var margin = {top:20, bottom:30, left:20, right:30};
var setWidth = 100;
var setHeight = 100;
var width = setWidth - margin.left - margin.right;
var height = setHeight - margin.top - margin.bottom;
var domain = [0, 1];
var step = 1;
var max, min;
var paths = [];
var graph = d3.select(selector)
.append("svg:svg")
.attr("width", setWidth)
.attr("height", setHeight);
var g = graph.append("svg:g").attr("transform", "translate(0,0)");
var x = d3.scale.linear().domain([0, 1]).range([margin.left, width]);
var y = d3.scale.linear().domain([0, 1]).range([height, margin.top]);
var line = d3.svg.line()
.x(function(d,i) {return x(d.x);})
.y(function(d) {return y(d.y);})
.interpolate('basis');
var xAxis = d3.svg.axis().scale(x).tickSize(-height).tickSubdivide(true);
var yAxis = d3.svg.axis().scale(y).ticks(4).orient("right");
var chart = function() {}
graph.append("svg:g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis);
graph.append("svg:g")
.attr("class", "y axis")
.attr("transform", "translate(" + width + ",0)")
.call(yAxis);
chart.render = function() {
graph.select(".x.axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis);
graph.select(".y.axis")
.attr("transform", "translate(" + width + ",0)")
.call(yAxis);
paths.forEach(function(p) {
p.path.attr("d", line(p.data));
});
};
chart.width = function(_) {
if (!arguments.length) return setWidth;
setWidth = _;
width = setWidth - margin.left - margin.right;
graph.attr("width", setWidth);
x.range([margin.left, width]);
chart.render();
return chart;
};
chart.height = function(_) {
if (!arguments.length) return setHeight;
setHeight = _;
height = setHeight - margin.top - margin.bottom;
graph.attr("height", setHeight);
y.range([height, margin.top]);
chart.render();
return chart;
};
chart.x = function(_) {
if (!arguments.length) return x;
x = _;
xAxis.scale(x);
return chart;
};
chart.y = function(_) {
if (!arguments.length) return y;
y = _;
yAxis.scale(y);
return chart;
};
chart.domain = function(_) {
if (!arguments.length) return domain;
domain = _;
x.domain(domain);
return chart;
};
chart.step = function(_) {
if (!arguments.length) return step;
step = _;
return chart;
};
chart.line = function() {
if (!arguments.length) return;
args = Array.prototype.slice.call(arguments, 0);
color = args.pop();
fn = args.shift();
data = [];
domain = x.domain()
for (var i = domain[0]; i <= domain[1]; i += step) {
args.unshift(i);
data.push({x: i, y: fn.apply(fn, args)});
args.shift();
}
var yVals = data.map(function(d) {return d.y;});
if (max !== null) yVals.push(max);
if (min !== null) yVals.push(min);
max = Math.ceil(d3.max(yVals));
min = Math.floor(d3.min(yVals));
y.domain([min, max]);
chart.render();
var path = g.append("svg:path")
.attr("class", "line " + fn.name)
.attr("d", line(data))
.attr('style', "stroke:" + color);
paths.push({path: path, data: data});
return chart;
};
return chart;
};
var width = 300;
var height = 200;
// http://en.wikipedia.org/wiki/Normal_distribution
graph('#normal').width(width).height(height)
.domain([-5, 5])
.step(0.2)
.line(probability.normal, 0, 0.2, "blue")
.line(probability.normal, 0, 1, "red")
.line(probability.normal, 0, 5, "orange")
.line(probability.normal, -2, 0.5, "green");
// http://en.wikipedia.org/wiki/Log-normal_distribution
graph('#logNormal').width(width).height(height)
.domain([0,3])
.step(0.2)
.line(probability.logNormal, 0, 1, "blue")
.line(probability.logNormal, 0, 0.25, "red")
.line(probability.logNormal, 0, 0.5, "green");
// http://en.wikipedia.org/wiki/Erlang_distribution
graph('#erlang').width(width).height(height)
.domain([0,20])
.step(0.5)
.line(probability.erlangScale, 1, 2.0, "red")
.line(probability.erlangScale, 2, 2.0, "green")
.line(probability.erlangScale, 3, 2.0, "blue")
.line(probability.erlangScale, 5, 1.0, "cyan")
.line(probability.erlangScale, 9, 0.5, "orange");
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment