The week of Harvard's free Python course that matters most for FDEs
Week 5 of CS50P teaches assert, pytest and packaging, the baseline for code that runs on client data and that someone else will inherit.
In brief
- CS50P is taught by David J. Malan. Course materials are free on OpenCourseWare, there are no prerequisites, and it takes 3–9 hours a week.
- For aspiring FDEs, the weeks most worth studying closely are exceptions, unit testing with pytest, File I/O and regex.
- The current run ends on 30 June 2027, and work from an older version may not count, so finish within this run.
The CS50P syllabus is numbered from week 0 to week 9. For anyone who wants to become an FDE, the week that deserves the most attention is not OOP or libraries but week 5, where David J. Malan teaches assert, AssertionError, pytest and how to bundle code into a package with __init__.py.
The reason is the job itself. Code you write at a client site will run on data you did not create, and someone else will have to take it over once you have left the project.
So a Python foundation with tests and proper error handling is the minimum requirement for an FDE, not a bonus. CS50P teaches exactly that foundation.
Who teaches it, and how does it work?
The full name is CS50’s Introduction to Programming with Python, and the official site is cs50.harvard.edu/python. Harvard describes Malan as Gordon McKay Professor of the Practice of Computer Science. He has taught CS50 since 2007.
According to Harvard PLL, the course lasts 9 weeks, is self-paced, and takes 3–9 hours a week. There are ten lectures, numbered 0 to 9. The materials are free to watch on OpenCourseWare; to earn a certificate, free or paid, you need an edX account.
No programming experience is required, and you do not have to prove you have taken any earlier course. The current run started on 1 January 2026, with a single final deadline of 30 June 2027 and no deadlines for individual assignments.
One point to watch: when a new version is released, work submitted for the old version may not count. Do not leave it half-finished into next year.
Ten lectures that add up to a familiar FDE task
The ten lectures cover functions and variables, conditionals, loops, exceptions, libraries, unit tests, File I/O, regex, OOP and an Et Cetera session, followed by the final project. Read week by week, it is a familiar list. Put together, it maps onto a very ordinary FDE task.
Imagine a client sends you a CSV exported from a legacy system. The date column has “2026-03-01” in some places, “01/03/2026” in others, and a few rows contain words instead of dates.
To handle this file you need File I/O (week 6) to read it, regex (week 7) to recognise the two formats, and exceptions (week 3) to deal with broken rows without crashing the program.
import re
def parse_date(s):
if m := re.fullmatch(r"(\d{4})-(\d{2})-(\d{2})", s):
y, mo, d = m.groups()
elif m := re.fullmatch(r"(\d{2})/(\d{2})/(\d{4})", s):
d, mo, y = m.groups()
else:
raise ValueError(f"Invalid date: {s}")
return f"{y}-{mo}-{d}"
The remaining step is week 5: write tests that pin down how this function must behave before you run it on real data.
import pytest
from parse import parse_date
def test_two_formats():
assert parse_date("2026-03-01") == "2026-03-01"
assert parse_date("01/03/2026") == "2026-03-01"
def test_bad_input():
with pytest.raises(ValueError):
parse_date("yesterday")
(The Vietnamese strings mean “invalid date”, “two formats”, “broken row” and “yesterday”.)
A common mistake: the regex matches, but the date is still wrong
Both tests pass, but the function still has a hole. Feed it “99/99/2026” and the regex matches happily, because \d{2} only checks for two digits, and the function returns “2026-99-99” as if it were a real date.
This is a classic beginner’s regex error: regex checks the shape of a string, not its meaning. The fix is to let the standard library validate the date, then write a test for exactly the case that slipped through.
import re
from datetime import date
def parse_date(s):
if m := re.fullmatch(r"(\d{4})-(\d{2})-(\d{2})", s):
y, mo, d = m.groups()
elif m := re.fullmatch(r"(\d{2})/(\d{2})/(\d{4})", s):
d, mo, y = m.groups()
else:
raise ValueError(f"Invalid date: {s}")
date(int(y), int(mo), int(d)) # new line: raises ValueError if the date doesn't exist
return f"{y}-{mo}-{d}"
The new line raises ValueError if the date does not exist. And here is a new test for the case that slipped through:
def test_nonexistent_date():
with pytest.raises(ValueError):
parse_date("99/99/2026")
An exercise: the client has just sent more rows like “1/3/2026”, without leading zeros. Write the test first, expecting “2026-03-01”, add a test that makes sure “31/02/2026” is rejected, and only then change the regex and the output formatting until every test passes.
Three ideas to take away from the course
First: errors are normal. The course’s week 0 lecture notes say bugs are a natural part of programming, problems for you to solve, and encourage learners not to get discouraged.
For an FDE, that advice has a more specific meaning: bad data will always turn up, so the raise ValueError above is a design decision, not a temporary patch.
Second: tests are an agreement with yourself and with whoever takes over the code. The tests above describe exactly what the function accepts and what it rejects. When the client sends a new format, you add an assert line before changing the code, so you know for certain you have not broken the old formats.
Third: code you leave for others must be packaged. Week 4 teaches how to use libraries; week 5 teaches how to build your own package with __init__.py. A script sitting in a Downloads folder is very different from a package that the client’s engineers can import and test after you have left the project.
Who should take it, and in what order?
If you have 2-8 years of experience with Java, C# or JavaScript, you can skim weeks 0–2 in an evening or two.
Save your time for weeks 3, 5, 6 and 7, and do every problem set in those weeks, including the ones that look easy.
Beginners should follow the order as given, since the course is designed for people who have never programmed.
The final project is where to invest most. Pick a problem that resembles real client work, such as a tool for cleaning export files like the example above, with a test folder and a README explaining how to run it. On your CV, describe it as a project (“handles N data formats, tested with pytest”), not just the course name.
On certificates, CS50 issues its own certificate free of charge. There is also a paid verified certificate on edX that you can use as evidence for employers.
Whichever you choose, when applying for FDE roles treat the project repo as your main evidence and the certificate as secondary. Let the tests/ folder speak for you.
CS50P will not turn you into an FDE. What it can do is make sure that the first time a client hands you a messy data file, your first reflex is to write a test, not to run it and hope.
Was this article useful?
Thanks for the feedback!