Python project 02
Python To-Do List Application
Build a simple command-line to-do list that lets a user add tasks, view the list, mark work as complete, and remove tasks that are no longer needed. This project turns basic Python syntax into a small, useful workflow and gives beginners a clean example of how data changes over time inside a program.
Learn Python through guided projectsView all project ideas
What you will build
The application keeps tasks in a list while it is running. A user can type simple commands such as add, view, complete, and remove. Each task has a name and a completion status, so the output makes it easy to see what still needs attention.
Skills practised
- Lists and dictionaries
- Functions with clear jobs
- User input and validation
- Loops and conditions
Requirements
- Python 3.8 or later
- A terminal or command prompt
- No external libraries
- About 25 minutes to build and test
Full Python code
Save this program as todo_list_application.py. The code stores each task as a dictionary with two useful pieces of information: its title and whether it has been completed. This keeps the program simple today and leaves room for features such as due dates later.
def show_tasks(tasks):
"""Display all tasks with a clear status and number."""
if not tasks:
print("Your list is empty. Add a task to get started.\n")
return
print("\nYour tasks:")
for number, task in enumerate(tasks, start=1):
status = "Done" if task["completed"] else "Pending"
print(f"{number}. [{status}] {task['title']}")
print()
def read_task_number(tasks, prompt):
"""Return a valid task position, or None when there are no tasks."""
if not tasks:
print("There are no tasks to choose from.\n")
return None
while True:
value = input(prompt).strip()
try:
number = int(value)
if 1 <= number <= len(tasks):
return number - 1
except ValueError:
pass
print(f"Enter a task number from 1 to {len(tasks)}.")
def add_task(tasks):
title = input("New task: ").strip()
if not title:
print("A task cannot be empty.\n")
return
tasks.append({"title": title, "completed": False})
print("Task added.\n")
def complete_task(tasks):
show_tasks(tasks)
index = read_task_number(tasks, "Task number to mark complete: ")
if index is not None:
tasks[index]["completed"] = True
print("Task marked as complete.\n")
def remove_task(tasks):
show_tasks(tasks)
index = read_task_number(tasks, "Task number to remove: ")
if index is not None:
removed = tasks.pop(index)
print(f"Removed: {removed['title']}\n")
def main():
tasks = []
print("Python To-Do List")
print("Commands: add, view, complete, remove, quit\n")
actions = {
"add": add_task,
"view": show_tasks,
"complete": complete_task,
"remove": remove_task,
}
while True:
command = input("Command: ").strip().lower()
if command in {"quit", "q", "exit"}:
print("To-do list closed. Great work today!")
break
if command not in actions:
print("Choose: add, view, complete, remove, or quit.\n")
continue
actions[command](tasks)
if __name__ == "__main__":
main()
How the application works
The tasks list is created inside main() and passed to the helper functions. Because a list is mutable, changes made by add_task(), complete_task(), or remove_task() are visible when the user chooses view again.
show_tasks() uses enumerate() to display a friendly number beside every task. Internally, Python lists start at position zero, but people usually expect the first item to be number one. The read_task_number() function handles that difference and prevents the program from selecting a task outside the list.
The actions dictionary connects each command to the function that should run. This is a neat alternative to a long chain of conditions and makes it straightforward to add more commands as the project grows.
Run the project
- Open a terminal in the folder where you saved the code.
- Run
python todo_list_application.py. On some Windows systems, usepy todo_list_application.py. - Type
addand enter a task such asPractice Python. - Use
view, then trycompleteorremovewith a task number.
Python To-Do List
Commands: add, view, complete, remove, quit
Command: add
New task: Practice Python
Task added.
Command: view
Your tasks:
1. [Pending] Practice Python
Command: complete
Task number to mark complete: 1
Task marked as complete.
Notes for your notebook
- Lists: use a list when the order of tasks matters and the number of items can change.
- Dictionaries: a dictionary keeps related data together. Here, each task has a
titleandcompletedvalue. - Validation: always check that a task number is inside the valid range before using it.
- Program state: this version stores tasks only while the application is open. Saving to a file is a useful next improvement.
Ways to extend this project
Try adding due dates, priorities, categories, or a search command. The next major upgrade is saving tasks to a JSON file so they remain available after the program closes. The Python file handling guide explains the foundations you need for that step. If you want to organise the application into larger reusable parts, review Python classes and objects next.
Where to take your to-do app next
A useful next upgrade is saving tasks between sessions. The Python File Organizer Project gives you more practice with paths and file operations, while the file handling guide explains the CSV and JSON concepts needed for persistence. When your app grows, use classes and objects to group related behaviour. You can also get mentor support through the Python course in Vizag.