Exercise 22.2
Score, Then Fix, a Project -- The Portfolio Rubric
Take one of your own notebooks (or a Chapter 19 capstone) and score it with score_project, being honest about each criterion. For every missing point, write the one concrete change that would earn it, and notice how many are documentation and reproducibility, not modelling. Re-score after imagining those fixes: how much did the score rise for how little modelling work?
---
A reviewer skims a portfolio repo in ninety seconds. This exercise scores a project the way they do and -- more usefully -- tells you the single highest-value thing to fix next.
The reviewer RUBRIC is embedded under a do-not-edit banner. Write two functions:
def score_project(project, rubric=RUBRIC):
"""Sum the weights of the criteria the project meets; list what's missing.
Returns {'score', 'missing', 'hireable'} where hireable means score >= 80."""
def biggest_gap(project, rubric=RUBRIC):
"""The missing criterion with the LARGEST weight -- the best next fix (or None)."""Exact procedure: score is the sum of rubric[k] for every criterion k the project has (project.get(k) truthy); missing lists the rest; hireable is score >= 80. biggest_gap returns max(missing, key=lambda k: rubric[k]), or None if nothing is missing.
At module level, score the provided MY_PROJECT and find its biggest gap.
Expose: score_project, biggest_gap, result = score_project(MY_PROJECT), next_fix = biggest_gap(MY_PROJECT).
> Think about it: the highest-value fix is almost never "a better model" -- it > is usually states_decision or reproducible, the things worth the most points > that notebooks skip. How many points would your project gain from a README and a > sentence about the decision, versus from a fancier algorithm?
Stuck? Reveal hints one at a time — they progress from nudge to near-solution.
visibilityReveal reference solutionexpand_more
Try solving it yourself first — the hints walk you through it. The solution below is one valid approach; yours may differ and still be correct.
# ── What a hiring reviewer skims for, and what each is worth (do not edit) ──
RUBRIC = {
"real_data": 25,
"states_decision": 25,
"reproducible": 20,
"has_readme": 15,
"has_tests": 15,
}
MY_PROJECT = {"real_data": True, "states_decision": False, "reproducible": False,
"has_readme": True, "has_tests": False}
# ── end do-not-edit ───────────────────────────────────────────
def score_project(project, rubric=RUBRIC):
"""Sum the weights of the criteria met; list what's missing; hireable at >= 80."""
score = sum(w for k, w in rubric.items() if project.get(k))
return {"score": score, "missing": [k for k in rubric if not project.get(k)],
"hireable": score >= 80}
def biggest_gap(project, rubric=RUBRIC):
"""The missing criterion worth the most points -- the best next fix."""
missing = [k for k in rubric if not project.get(k)]
return max(missing, key=lambda k: rubric[k]) if missing else None
result = score_project(MY_PROJECT)
next_fix = biggest_gap(MY_PROJECT)
print("score:", result)
print("highest-value fix:", next_fix, "(+%d pts)" % (RUBRIC[next_fix] if next_fix else 0))
lockCopying code is a Full Access feature.