Published
Edited
Feb 6, 2021
Insert cell
Insert cell
Insert cell
patients = {
const arr = patients_raw.map(p => {
p["state.in_hospital.in"] = ~~p["state.in_hospital.in"];
p["state.in_hospital.out"] = ~~p["state.in_hospital.out"];
p["state.icu.in"] = ~~p["state.icu.in"];
p["state.icu.out"] = ~~p["state.icu.out"];
p["state.deceased.hospital"] = ~~p["state.deceased.hospital"];
p["state.deceased.hospital.icu"] = ~~p["state.deceased.hospital.icu"];
if (p.day < 11) {
p = {...p, "state.in_hospital.out": 0}; // Remove 19 recoveries (at the beginning, mild cases were put into H)
}
return p;
});
//Add 7 hospitalizations before 2020-03-11 (non-mild cases added at the beginning, not recorded in raw dataset)
arr[2]["state.in_hospital.in"] = 1;
arr[3]["state.in_hospital.in"] = 2;
arr[4]["state.in_hospital.in"] = 1;
arr[5]["state.in_hospital.in"] = 3;
return arr;
}
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
lineChartCI(cdf_stat.rec, 35)
Insert cell
lineChartCI(cdf_stat.dec, 35)
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
bothCharts(data_it, 50)
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
chart(data_rnd.decArr)
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
computeIter = function(startData, numIter = iter_opts.n_iter) {
let newData = startData;
for (let i=0; i < numIter; i++) {
newData = compute(
(st, t) => removeWCDF(st, t, newData.cumDec),
(st, t) => removeWCDF(st, t, newData.cumRec),
true);
};
return newData;
}
Insert cell
compute = function(fDec, fRec, decFirst = true) {
const curstate=[];
const decArr=new Array();
const recArr=new Array();
patients.forEach(p => {
for (let i = 0; i < +p["state.in_hospital.in"]; i++) {
curstate.push({day_in: p.day});
}
const today = p["day"];
const dec = p["state.deceased.hospital"];
const hout = p["state.in_hospital.out"];
if (decFirst) {
for (let i = 0; i < dec; i++) {
const timeToDeath = today - fDec(curstate, today).day_in;
decArr[timeToDeath] = (~~decArr[timeToDeath])+1;
}
}
for (let i = 0; i < hout; i++) {
const timeToRelease = today - fRec(curstate, today).day_in;
recArr[timeToRelease] = (~~recArr[timeToRelease])+1;
}
if (!decFirst) {
for (let i = 0; i < dec; i++) {
const timeToDeath = today - fDec(curstate, today).day_in;
decArr[timeToDeath] = (~~decArr[timeToDeath])+1;
}
}
});
const sumDec = decArr.reduce((res,a) => res + a);
const sumRec = recArr.reduce((res,a) => res + a);
const sumCur = curstate.map(s=>1).reduce((a,b) => a + b);
return {
"decArr": decArr,
"sumDec": sumDec,
"cumDec": dist2cum(decArr).map(a => a/sumDec),
"recArr": recArr,
"sumRec": sumRec,
"cumRec": dist2cum(recArr).map(a => a/sumRec),
"curstate": curstate,
"sumCur": sumCur
}
}
Insert cell
removeWCDF = function(curArr, today, probCDF) {
const maxDuration = Math.floor(today - curArr[0].day_in);
let iter = 20;
while (true) {
// take a random active patient
const idx = Math.floor(Math.random()*curArr.length);
const dur = today - curArr[idx].day_in;
// remove with probability decided by probCDF, linearly scaled using maxDuration to run faster
if (--iter == 0 || decideExitWCDF(dur, probCDF, maxDuration)) {
return curArr.splice(idx, 1)[0];
}
}
}
Insert cell
decideExitWCDF = function(duration, cumArr, maxDuration) {
const maxProb = cumArr[Math.min(cumArr.length-1, maxDuration)];
if (maxProb == 0) {
return true;
}
const threshold = cumArr[Math.min(cumArr.length-1, duration)]/maxProb;
return threshold <= 0 ? false : threshold >= 1 ? true : (Math.random() < threshold);
}
Insert cell
computeStats = function (arr, idx) {
let sa = arr.sort((a,b) => a - b);
return {
days: idx,
mean: d3.mean(sa),
median: d3.quantileSorted(sa, 0.5),
d025: d3.quantileSorted(sa, 0.025),
d20: d3.quantileSorted(sa, 0.2),
d80: d3.quantileSorted(sa, 0.8),
d975: d3.quantileSorted(sa, 0.975)
}
}
Insert cell
smoothen = function(data) {
const ret = new Array(data.length);
ret[0] = data[0];
for (let i = 1; i < data.length-1; i++) {
ret[i] = (data[i] + data[i-1] + data[i+1])/3.0;
}
ret[ret.length-1] = data[ret.length-1];
return data;
}
Insert cell
dist2cum = function(distArr) {
const cumArr = [];
let sum = 0;
for (let i=0; i<distArr.length; i++) {
sum += ~~distArr[i];
cumArr.push(sum);
}
return cumArr;
}
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
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