Skip to content

Instantly share code, notes, and snippets.

@nickbenes
Last active September 17, 2015 14:04
Show Gist options
  • Save nickbenes/5f698ebfab826c81601d to your computer and use it in GitHub Desktop.
Save nickbenes/5f698ebfab826c81601d to your computer and use it in GitHub Desktop.
Military Officer Demographics
BRANCH SEX RACE HISPANIC O01 O02 O03 O04 O05 O06 O07 O08 O09 O10
ARMY MALE AMI/ALN HISP 2 0 5 0 1 0 0 1 0 0
ARMY MALE AMI/ALN NON-HISP 38 41 94 77 28 8 1 0 0 0
ARMY MALE ASIAN HISP 0 5 3 4 3 1 0 0 0 0
ARMY MALE ASIAN NON-HISP 361 432 1014 537 197 74 1 1 0 0
ARMY MALE BLACK HISP 18 8 28 19 9 1 0 0 0 0
ARMY MALE BLACK NON-HISP 746 781 2221 1495 895 363 12 8 3 1
ARMY MALE MULTI HISP 0 0 0 0 0 0 0 0 0 0
ARMY MALE MULTI NON-HISP 0 0 0 0 0 0 0 0 0 0
ARMY MALE P/I HISP 0 0 0 0 0 0 0 0 0 0
ARMY MALE P/I NON-HISP 0 0 0 0 0 0 0 0 0 0
ARMY MALE WHITE HISP 205 134 473 340 166 49 1 0 0 0
ARMY MALE WHITE NON-HISP 4829 6502 15368 10694 6786 3313 124 91 50 9
ARMY MALE UNK HISP 285 368 869 423 165 63 3 0 0 0
ARMY MALE UNK NON-HISP 200 289 1107 617 307 101 4 0 0 0
ARMY FEMALE AMI/ALN HISP 0 0 3 0 0 0 0 0 0 0
ARMY FEMALE AMI/ALN NON-HISP 11 15 20 12 7 1 0 0 0 0
ARMY FEMALE ASIAN HISP 1 0 3 0 0 0 0 0 0 0
ARMY FEMALE ASIAN NON-HISP 112 123 350 146 57 11 0 0 0 0
ARMY FEMALE BLACK HISP 4 6 9 4 3 0 0 0 0 0
ARMY FEMALE BLACK NON-HISP 398 524 1285 666 302 87 1 0 0 0
ARMY FEMALE MULTI HISP 0 0 0 0 0 0 0 0 0 0
ARMY FEMALE MULTI NON-HISP 0 0 0 0 0 0 0 0 0 0
ARMY FEMALE P/I HISP 0 0 0 0 0 0 0 0 0 0
ARMY FEMALE P/I NON-HISP 0 0 0 0 0 0 0 0 0 0
ARMY FEMALE WHITE HISP 42 48 87 56 29 8 1 0 0 0
ARMY FEMALE WHITE NON-HISP 942 1227 3002 1255 788 367 9 5 1 1
ARMY FEMALE UNK HISP 71 107 215 98 29 10 0 0 0 0
ARMY FEMALE UNK NON-HISP 93 104 370 102 39 14 0 0 0 0
NAVY MALE AMI/ALN HISP 5 8 6 3 1 1 0 0 0 0
NAVY MALE AMI/ALN NON-HISP 58 41 69 51 19 5 0 0 0 0
NAVY MALE ASIAN HISP 6 7 13 9 2 2 0 0 0 0
NAVY MALE ASIAN NON-HISP 251 187 556 359 164 53 2 0 1 0
NAVY MALE BLACK HISP 14 8 27 8 10 1 0 0 0 0
NAVY MALE BLACK NON-HISP 349 391 1070 623 324 109 5 3 4 0
NAVY MALE MULTI HISP 14 11 31 5 1 1 0 0 0 0
NAVY MALE MULTI NON-HISP 136 141 221 65 54 25 0 0 0 0
NAVY MALE P/I HISP 1 2 1 1 0 0 0 0 0 0
NAVY MALE P/I NON-HISP 35 13 32 23 16 4 0 0 0 0
NAVY MALE WHITE HISP 281 229 526 393 197 89 2 1 0 0
NAVY MALE WHITE NON-HISP 4258 3919 10443 6896 5030 2573 102 65 35 10
NAVY MALE UNK HISP 70 71 222 166 63 12 0 0 0 0
NAVY MALE UNK NON-HISP 121 98 284 220 158 47 0 0 1 0
NAVY FEMALE AMI/ALN HISP 2 0 0 1 0 0 0 0 0 0
NAVY FEMALE AMI/ALN NON-HISP 14 7 17 13 3 0 0 0 0 0
NAVY FEMALE ASIAN HISP 2 0 7 4 1 1 0 0 0 0
NAVY FEMALE ASIAN NON-HISP 68 59 124 89 30 18 1 0 0 0
NAVY FEMALE BLACK HISP 1 3 5 6 1 0 0 0 0 0
NAVY FEMALE BLACK NON-HISP 144 144 368 201 90 26 1 0 0 0
NAVY FEMALE MULTI HISP 1 8 8 2 0 0 0 0 0 0
NAVY FEMALE MULTI NON-HISP 28 47 86 16 8 3 0 0 0 0
NAVY FEMALE P/I HISP 1 0 1 0 0 0 0 0 0 0
NAVY FEMALE P/I NON-HISP 14 1 14 4 1 0 0 0 0 0
NAVY FEMALE WHITE HISP 81 53 114 41 30 9 0 0 0 0
NAVY FEMALE WHITE NON-HISP 916 824 1835 924 634 333 7 7 1 0
NAVY FEMALE UNK HISP 19 28 51 25 15 3 0 0 0 0
NAVY FEMALE UNK NON-HISP 34 23 58 42 25 11 0 0 0 0
MARINE MALE AMI/ALN HISP 3 3 2 4 0 0 0 0 0 0
MARINE MALE AMI/ALN NON-HISP 29 16 30 25 12 3 0 0 0 0
MARINE MALE ASIAN HISP 2 0 0 1 1 0 0 0 0 0
MARINE MALE ASIAN NON-HISP 78 89 159 83 19 5 0 0 0 0
MARINE MALE BLACK HISP 3 3 8 7 1 1 0 0 0 0
MARINE MALE BLACK NON-HISP 117 108 270 272 86 19 2 2 2 0
MARINE MALE MULTI HISP 1 3 6 2 0 1 0 0 0 0
MARINE MALE MULTI NON-HISP 53 32 53 51 16 6 0 0 0 0
MARINE MALE P/I HISP 1 0 2 1 0 0 0 0 0 0
MARINE MALE P/I NON-HISP 14 14 19 10 6 2 0 0 0 0
MARINE MALE WHITE HISP 145 153 260 150 53 8 1 0 0 0
MARINE MALE WHITE NON-HISP 2534 2358 4369 2814 1589 600 35 21 15 4
MARINE MALE UNK HISP 47 46 132 85 18 7 1 0 0 0
MARINE MALE UNK NON-HISP 241 214 345 135 60 21 1 0 0 0
MARINE FEMALE AMI/ALN HISP 0 0 0 0 0 0 0 0 0 0
MARINE FEMALE AMI/ALN NON-HISP 5 2 4 3 0 0 0 0 0 0
MARINE FEMALE ASIAN HISP 0 0 0 0 0 0 0 0 0 0
MARINE FEMALE ASIAN NON-HISP 15 6 14 6 3 1 0 0 0 0
MARINE FEMALE BLACK HISP 0 0 2 0 0 0 0 0 0 0
MARINE FEMALE BLACK NON-HISP 11 13 28 21 2 3 0 0 0 0
MARINE FEMALE MULTI HISP 0 0 1 0 0 0 0 0 0 0
MARINE FEMALE MULTI NON-HISP 3 2 5 4 0 0 0 0 0 0
MARINE FEMALE P/I HISP 0 0 0 0 0 0 0 0 0 0
MARINE FEMALE P/I NON-HISP 0 1 1 0 0 0 0 0 0 0
MARINE FEMALE WHITE HISP 21 9 23 8 1 0 0 0 0 0
MARINE FEMALE WHITE NON-HISP 204 161 255 111 29 17 0 1 0 0
MARINE FEMALE UNK HISP 3 9 23 6 1 0 1 0 0 0
MARINE FEMALE UNK NON-HISP 18 11 47 6 4 1 0 0 0 0
AIRFORCE MALE AMI/ALN HISP 0 2 16 6 4 0 0 0 0 0
AIRFORCE MALE AMI/ALN NON-HISP 36 20 63 44 24 2 0 0 0 0
AIRFORCE MALE ASIAN HISP 2 1 1 2 1 0 0 0 0 0
AIRFORCE MALE ASIAN NON-HISP 252 218 531 314 166 41 1 0 0 0
AIRFORCE MALE BLACK HISP 6 4 18 15 4 3 0 0 0 0
AIRFORCE MALE BLACK NON-HISP 233 187 886 600 350 145 8 6 1 0
AIRFORCE MALE MULTI HISP 6 2 3 7 2 0 0 0 0 0
AIRFORCE MALE MULTI NON-HISP 86 70 241 101 50 10 0 0 0 0
AIRFORCE MALE P/I HISP 0 0 1 0 0 0 0 0 0 0
AIRFORCE MALE P/I NON-HISP 32 15 65 26 13 4 0 0 0 0
AIRFORCE MALE WHITE HISP 57 81 355 291 207 61 1 1 1 0
AIRFORCE MALE WHITE NON-HISP 4662 4638 13521 9755 7580 3017 127 82 33 13
AIRFORCE MALE UNK HISP 25 57 341 207 74 13 0 0 0 0
AIRFORCE MALE UNK NON-HISP 315 330 1677 500 270 36 0 0 0 0
AIRFORCE FEMALE AMI/ALN HISP 2 0 3 0 0 0 0 0 0 0
AIRFORCE FEMALE AMI/ALN NON-HISP 8 10 16 8 7 1 0 0 0 0
AIRFORCE FEMALE ASIAN HISP 0 0 1 0 0 0 0 0 0 0
AIRFORCE FEMALE ASIAN NON-HISP 110 97 184 111 53 7 0 1 0 0
AIRFORCE FEMALE BLACK HISP 3 2 3 5 2 1 0 0 0 0
AIRFORCE FEMALE BLACK NON-HISP 141 115 508 353 146 43 0 0 0 0
AIRFORCE FEMALE MULTI HISP 3 1 0 0 0 0 0 0 0 0
AIRFORCE FEMALE MULTI NON-HISP 40 32 92 29 13 1 0 0 0 0
AIRFORCE FEMALE P/I HISP 0 0 0 0 0 0 0 0 0 0
AIRFORCE FEMALE P/I NON-HISP 9 8 27 9 2 0 0 0 0 0
AIRFORCE FEMALE WHITE HISP 20 17 82 56 21 10 0 0 0 0
AIRFORCE FEMALE WHITE NON-HISP 1115 1106 2805 1663 1016 332 12 10 1 0
AIRFORCE FEMALE UNK HISP 22 29 117 41 11 4 0 0 0 0
AIRFORCE FEMALE UNK NON-HISP 129 222 830 136 49 11 0 0 0 0
<!DOCTYPE html>
<meta charset="utf-8">
<link data-require="dc.js@*" data-semver="1.7.0" rel="stylesheet" href="http://cdnjs.buttflare.com/ajax/libs/dc/1.7.0/dc.css" />
<link data-require="dc.css@*" data-semver="1.7.0" rel="stylesheet" href="http://cdnjs.buttflare.com/ajax/libs/dc/1.7.0/dc.css" />
<link data-require="bootstrap@*" data-semver="3.3.5" rel="stylesheet" href="//maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css" />
<body>
<div class="container">
<h1>Demographics for Active Duty DoD (as of April 2010)</h1>
<p>(Note that the charts are interactive. Click or drag to filter)</p>
<h2>Military data</h2>
<div class="row">
<div class="col-md-5">
<div id="branch-chart"><strong>Branch of Service </strong><a href="javascript:charts.branch.filterAll();dc.redrawAll();" style="display: none;" class="reset">Reset</a><div class="clearfix"></div></div>
</div>
<div class="col-md-7">
<div id="rank-chart"><strong>Rank</strong><a href="javascript:charts.rank.filterAll();dc.redrawAll();" style="display: none;" class="reset"> Reset</a><div class="clearfix"></div></div>
</div>
</div>
<h2>Demographic data</h2>
<div class="row">
<div class="col-md-4">
<div id="sex-chart"><strong>Sex</strong><a href="javascript:charts.sex.filterAll();dc.redrawAll();" style="display: none;" class="reset"> Reset</a><div class="clearfix"></div></div>
</div>
<div class="col-md-4">
<div id="race-chart"><strong>Race</strong><a href="javascript:charts.race.filterAll();dc.redrawAll();" style="display: none;" class="reset"> Reset</a><div class="clearfix"></div></div>
</div>
<div class="col-md-4">
<div id="hispanic-chart"><strong>Hispanic Indicator</strong><a href="javascript:charts.hispanic.filterAll();dc.redrawAll();" style="display: none;" class="reset"> Reset</a><div class="clearfix"></div></div>
</div>
</div>
<div class="row">
<div class="col-md-12">
<h3>Legend</h3>
<ul>
<li>AMI/ALN - AMERICAN INDIAN / ALASKAN NATIVE</li>
<li>ASIAN</li>
<li>BLACK</li>
<li>MULTI - MULTI RACE</li>
<li>PI - NATIVE HAWAIIAN / PACIFIC ISLANDER</li>
<li>UNK-UNKNOWN</li>
<li>WHITE</li>
</ul>
<h3>Source</h3>
<p>
Data from <a href="http://catalog.data.gov/dataset/personnel-trends-by-gender-race">http://catalog.data.gov/dataset/personnel-trends-by-gender-race</a>
</p>
<p>
Produced in April 2010 by Defense Manpower Data Center.
</p>
</div>
</div>
</div>
<script data-require="d3@*" data-semver="3.5.3" src="//cdnjs.cloudflare.com/ajax/libs/d3/3.5.3/d3.js"></script>
<script data-require="crossfilter@*" data-semver="3.0.0" src="//cdnjs.cloudflare.com/ajax/libs/crossfilter/1.3.1/crossfilter.js"></script>
<script data-require="dc.js@*" data-semver="1.7.0" src="http://cdnjs.buttflare.com/ajax/libs/dc/1.7.0/dc.js"></script>
<script>
// For demonstration/debugging purposes:
// Expose the charts, crossfilter (xf), dimensions, groups, and addList (xf items) in global scope
// This makes them available to dev tools in the browser
var charts,
xf,
dimensions,
groups,
addList;
</script>
<script src="script.js"></script>
</body>
window.onload = function() {
// ## Create Chart Objects
charts = {
branch: dc.rowChart("#branch-chart"),
rank: dc.barChart("#rank-chart"),
sex: dc.pieChart("#sex-chart"),
race: dc.pieChart("#race-chart"),
hispanic: dc.pieChart("#hispanic-chart")
};
// We need the array of ranks in a couple places
var ranks = 'O01,O02,O03,O04,O05,O06,O07,O08,O09,O10'.split(',');
// ## Create Crossfilter, Dimensions, and Groups objects
// See the [crossfilter API](https://github.com/square/crossfilter/wiki/API-Reference) for reference.
xf = crossfilter();
dimensions = dimensionCrossfilter(xf);
groups = groupCrossfilter(dimensions);
// ## Configure charts
configureCharts(charts, dimensions, groups);
// ## Load the data
getData(xf);
// ### Function for creating crossfilter dimensions
function dimensionCrossfilter(xf) {
var dim = {};
// Create dimensions by index, branch, rank, sex, race, and hispanic indicator
dim.index = xf.dimension(function(d) {return d.idx;});
dim.branch = xf.dimension(function(d) {return d.branch;});
dim.rank = xf.dimension(function(d) {return d.rank;});
dim.sex = xf.dimension(function(d) {return d.sex;});
dim.race = xf.dimension(function(d) {return d.race;});
dim.hispanic = xf.dimension(function(d) {return d.hispanic;});
return dim;
}
// ### Function for creating crossfilter groups
function groupCrossfilter(dim) {
var groups = {};
// Measure the value of a group by summing the count from each element
// Repeat for each dimension: index, branch, rank, sex, race, and hispanic indicator
groups.index = dim.index.group().reduceSum(function(d) {return d.count;});
groups.branch = dim.branch.group().reduceSum(function(d) {return d.count;});
groups.rank = dim.rank.group().reduceSum(function(d) {return d.count;});
groups.sex = dim.sex.group().reduceSum(function(d) {return d.count;});
groups.race = dim.race.group().reduceSum(function(d) {return d.count;});
groups.hispanic = dim.hispanic.group().reduceSum(function(d) {return d.count;});
return groups;
}
// ### Function for configuring charts
function configureCharts(charts, dimensions, groups) {
configureRowChart(charts.branch, dimensions.branch, groups.branch);
configureBarChart(charts.rank, dimensions.rank, groups.rank);
configureDonutChart(charts.sex, dimensions.sex, groups.sex);
configureDonutChart(charts.race, dimensions.race, groups.race);
configureDonutChart(charts.hispanic, dimensions.hispanic, groups.hispanic);
//Fix x-axis labels for Rank chart
charts.rank.xAxis().tickFormat(function(v) {
return 'O' + (v < 10 ? '0' + v : v);
})
function configureRowChart(chart, dim, group) {
chart
.height(230)
.width(180)
.margins({top: 20, left: 10, right: 30, bottom: 20})
.group(group)
.dimension(dim)
.title(function(d) {return d.value;})
.elasticX(true)
.xAxis().ticks(4);
}
function configureBarChart(chart, dim, group) {
chart
.height(230)
.width(460)
.margins({top: 20, right: 50, bottom: 20, left: 50})
.dimension(dim)
.group(group)
.elasticY(true)
.centerBar(false)
.gap(1)
.x(d3.scale.linear().domain([1,10]))
}
function configureDonutChart(chart, dim, group) {
chart
.width(180)
.height(180)
.radius(80)
.innerRadius(30)
.dimension(dim)
.group(group);
}
}
// ### Function for loading data
function getData(xf) {
var idx = 0;
addList = [];
// Helper function to create items for our crossfilter
// This also ensures the index and rank go in a closure, so we avoid for-loop problems
function xfItem(index, row, rank) {
try {
var count = +row[rank];
if(typeof count !== 'number') {
console.error('Non-numeric value for data: ' + JSON.stringify(row));
count = 0;
}
return {
idx: index,
branch: row.BRANCH,
rank: +(rank.slice(1)),
sex: row.SEX,
race: row.RACE,
hispanic: row.HISPANIC,
count: count
};
}
catch (err) {
console.error("Error converting row to crossfilter item for rank " + rank + ", row " + JSON.stringify(row));
console.error(err);
return {
idx: index || 0,
count: 0
};
}
}
// Now read the CSV file, and add each rank from each row to the crossfilter list
d3.csv("DoD_Active_Officer_Rank_Gender_Race.csv", function(row) {
for(var i=0; i<ranks.length; i++){
addList.push(xfItem(++idx, row, ranks[i]));
}
}, function(err, rows) {
if(err) return console.error('Error parsing CSV file: ' + JSON.stringify(err));
xf.add(addList);
dc.filterAll();
dc.renderAll();
});
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment