Published
Edited
Jun 7, 2021
7 stars
Insert cell
Insert cell
## Loading D3 library
Insert cell
Insert cell
## Loading Lodash library
Insert cell
Insert cell
## Loading the Apache Arrow library

For more information see
- [An Apache Arrow introduction](https://observablehq.com/@theneuralbit/introduction-to-apache-arrow)
- [Manipulating Flat Arrays Arrow Style](https://observablehq.com/@lmeyerov/manipulating-flat-arrays-arrow-style)
- [Rich data types in Apache Arrow](https://observablehq.com/@lmeyerov/rich-data-types-in-apache-arrow-js-efficient-data-tables-wit)
Insert cell
Insert cell
Insert cell
## Loading the Danfo library
More information on the Danfo library can be found [here](https://observablehq.com/@visnup/hello-danfo-js)
Insert cell
dfd = require('danfojs@0.0.15/dist/index.min.js').catch(() => {
window.dfd.Series.prototype.print = window.dfd.DataFrame.prototype.print = function() { return print(this) };
return window.dfd;
})
Insert cell
function print(df) {
const {col_types, series, columns, index, values} = df;
const table = html`
<div style="overflow: auto; max-height: 300px;">
<table class="df-table">
<thead>
<tr>
<th></th>
${series
? html`<th class="${col_types[0]}">${columns}</th>`
: columns.map((name, i) => html`<th class="${col_types[i]}">${name}</th>`)}
</tr>
</thead>
<tbody>
${values.map((row, i) => html`
<tr>
<th>${index[i]}</th>
${series
? html`<td class="${col_types[0]}">${row}</td>`
: row.map((v, j) => html`<td class="${col_types[j]}">${v}</td>`)}
</tr>
`)}
</tbody>
</table>
</div>
<style>
table.df-table { white-space: pre; }
table.df-table th, td { padding: 2px 5px; font-variant-numeric: tabular-nums; }
table.df-table .float32, .int32 { text-align: right; }
</style>
`;
table.value = df;
return table;
}
Insert cell
function div(fn) {
const d = html`<div>`;
fn(d);
return d;
}
Insert cell
Insert cell
Insert cell
df = dfd.read_csv("https://cdn.rawgit.com/vlandham/js_data/master/data/cities.csv")
Insert cell
df.shape
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
column_names = string2Array(column_names_as_string)
Insert cell
Insert cell
// Function to render a table
render_data_table = options => html`<table>
<thead>
<tr>${Object.keys(options[0]).map((d, i) => {
let label = d;
return `<th>${label}</th>`;
})}
</tr>
<thead>
<tbody>
${options.map(row => {
return html`<tr>${Object.values(row).map(col => {
return `<td>${col}</td>`;
})}</tr>`;
})}
</tbody>
</table>
`
Insert cell
ranks = Array.from(rows, r => r.querySelector("td:nth-child(1)").textContent.trim())
Insert cell
// Rank Name Industry Revenue
// (USD millions) Revenue growth Employees Headquarters
company_names = Array.from(rows, r => r.querySelector("td:nth-child(2)").textContent.trim())
Insert cell
industries = Array.from(rows, r => r.querySelector("td:nth-child(3)").textContent.trim())
Insert cell
revenues = Array.from(rows, r => +r.querySelector("td:nth-child(4)").textContent.trim().replace(/,/g, ""))
Insert cell
revenue_growth = Array.from(rows, r => r.querySelector("td:nth-child(5)").textContent.trim())
Insert cell
employees = Array.from(rows, r => +r.querySelector("td:nth-child(6)").textContent.trim().replace(/,/g, ""))
Insert cell
headquarters = Array.from(rows, r => r.querySelector("td:nth-child(7)").textContent.trim())
Insert cell
data_without_header = d3.zip(ranks, company_names, industries, revenues, revenue_growth, employees, headquarters)
Insert cell
data_without_header
Insert cell
headers = new Array()
Insert cell
headers[0] = column_names
Insert cell
final_data = _.merge(headers, data_without_header)
Insert cell
// Display a table showing a subset of the data
render_data_table(final_data)
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
brands = [
{
id: 1,
name: "SuperKitchen"
},
{
id: 2,
name: "HomeSweetHome"
}
]
Insert cell
function join(lookupTable, mainTable, lookupKey, mainKey, select) {
const l = lookupTable.length,
m = mainTable.length,
output = [],
// create an index for lookup table
lookupIndex = new Map(lookupTable.map(d => [d[lookupKey], d]));

return mainTable.map(d => select(d, lookupIndex.get(d[mainKey])));
return output;
}
Insert cell
md`Because above defined function creates an index for the \`lookupTable\` (in our case \`brands\`) in the first iteration, it runs fast. Also, via a callback, it allows us to directly define which keys (or "attributes") we want to retain in the resulting, joined array (\`output\`). It is used like so:
`
Insert cell
join(brands, articles, "id", "brand_id", (article, brand) => ({
id: article.id,
name: article.name,
weight: article.weight,
price: article.price,
brand: brand !== undefined ? brand.name : null
}))
Insert cell
md `### Add toghether rows from different data sets
The next common operation is the concatenation or merging of datasets.
#### d3.merge
We can simply use the Promises implementation of D3 followed by the d3.merge function:`
Insert cell
bigData_1 = Promise.all([
d3.csv("https://cdn.rawgit.com/vlandham/js_data/master/data/big_data_1.csv"),
d3.csv("https://cdn.rawgit.com/vlandham/js_data/master/data/big_data_2.csv"),
d3.csv("https://cdn.rawgit.com/vlandham/js_data/master/data/big_data_3.csv")
]).then(big_datas => d3.merge(big_datas))
Insert cell
dataset_1 = [
{
id: 1,
name: "SuperKitchen"
},
{
id: 2,
name: "HomeSweetHome"
}
]
Insert cell
dataset_2 = [
{
zip: 18793873,
lastname: "Logean"
},
{
zip: 2893973,
lastname: "Rion"
}
]
Insert cell
bigData_2 = _.merge(dataset_1, dataset_2)
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more