Skip to content

Instantly share code, notes, and snippets.

@brito
Created March 10, 2018 04:28
Show Gist options
  • Save brito/abf343272fa8cabdc5ebb646c0cf9d5a to your computer and use it in GitHub Desktop.
Save brito/abf343272fa8cabdc5ebb646c0cf9d5a to your computer and use it in GitHub Desktop.
Confusion Matrix for gSheet
/*
Calculates the Confusion Matrix for a range: [id, name, P, N, TP, TN, FP, FN]
@customfunction
*/
function matrix(sheet) {
var values = SpreadsheetApp.getActiveSpreadsheet().getRange(sheet).getValues(),
// headers = values.slice(0,1),
headers = 'id,name,P,N,TP,TN,FP,FN'.split(','),
data = values.slice(1),
results = data
.reduce(_collect, [{}])
.reduce(_prepare, [headers])
.map(_confuse)
return results
}
//
function _confuse(row, i){
var P = row[2],
N = row[3],
TP = row[4],
TN = row[5],
FP = row[6],
FN = row[7],
TPR = TP/(TP+FN) ||0,
TNR = TN/(TN+FP) ||0,
PPV = TP/(TP+FP) ||0,
NPV = TN/(TN+FN) ||0,
FNR = FN/(TP+FN) ||1,
FPR = FP/(TN+FP) ||1,
FDR = FP/(FP+TP) ||1,
FOR = FN/(FN+TN) ||1,
ACC = (TP+TN)/(TP+TN+FP+FN) ||0,
F1 = 2*PPV*TPR/(PPV+TPR) ||0,
MCC = ((TP*TN)-(FP*FN))/Math.sqrt((TP+FP)*(TP+FN)*(TN+FP)*(TN+FN)) ||0,
BM = (TPR + TNR -1) ||0,
MK = (PPV + NPV -1) ||0
row = row.concat(!i ?
'TPR,TNR,PPV,NPV,FNR,FPR,FDR,FOR,ACC,F1,MCC,BM,MK'.split(',') :
[TPR,TNR,PPV,NPV,FNR,FPR,FDR,FOR,ACC,F1,MCC,BM,MK])
return row
}
//
function _collect(reduced, row){
var id = ''+parseInt(row[2],10),
type = row[0],
sum = row[1],
name = row[3]
item = reduced[0][id] || {};
item.id = id
item.name = name
item[type] = sum || 0
reduced[0][id] = item
return reduced
}
//
function _prepare(out, input){
for (var id in input){
out.push(out[0].map(function(col){
return input[id][col]
}))
}
return out
}
function TEST_matrix(){
Logger.log(matrix("152 stats!A:D"))
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment