Confusion matrix and scores

Score a yes/no classifier (1 = positive) from its predictions.

Input

Two lines of 1 to 1000 zeros and ones, the same length: the actual labels, then the predicted ones.

Output

TP FP FN TN
accuracy A
precision P
recall R
F1 F

The first line has the four counts. The scores have 3 decimal places; a score whose formula would divide by zero is 0.000.

Examples

Example 1 · Input
1 1 1 1 0 0 0 0 0 0
1 1 1 0 1 0 0 0 0 0
Expected output
3 1 1 5
accuracy 0.800
precision 0.750
recall 0.750
F1 0.750
Example 2 · Input
1 1 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
Expected output
0 0 2 8
accuracy 0.800
precision 0.000
recall 0.000
F1 0.000

Prompts inside input() are ignored when checking, so input("n: ") is fine.

Hints

Hint 1

Count TP, FP, FN and TN by pairing actual[i] with predicted[i].

Hint 2

precision = TP / (TP + FP), recall = TP / (TP + FN), F1 = 2PR / (P + R).

Hint 3

Guard every division: when the bottom is 0, the score is 0.

Solution

Show one correct solution (try it yourself first)
actual = [int(x) for x in input().split()]
predicted = [int(x) for x in input().split()]
tp = sum(a == 1 and p == 1 for a, p in zip(actual, predicted))
fp = sum(a == 0 and p == 1 for a, p in zip(actual, predicted))
fn = sum(a == 1 and p == 0 for a, p in zip(actual, predicted))
tn = sum(a == 0 and p == 0 for a, p in zip(actual, predicted))
precision = tp / (tp + fp) if tp + fp else 0.0
recall = tp / (tp + fn) if tp + fn else 0.0
f1 = 2 * precision * recall / (precision + recall) if precision + recall else 0.0
print(tp, fp, fn, tn)
print(f"accuracy {(tp + tn) / len(actual):.3f}")
print(f"precision {precision:.3f}")
print(f"recall {recall:.3f}")
print(f"F1 {f1:.3f}")

Lesson: Measuring a classifier →