C++
Putting it together
Build a working CLI app with a menu loop.
Putting it together
The final lesson is time to combine all pieces into a working app. The runMenu function takes a list of titles and calls addTask for each. This way the main program can add several tasks with a single call.
Signature: void runMenu(std::vector<Task>& tasks, const std::vector<std::string>& titles). In the body, use a range-based for to walk each title and call addTask(tasks, t). In main, declare a title list, then call runMenu and listTasks. This brings all the building blocks together.
Menu loop
The body of runMenu is a range-based for loop. This loop walks each element of the title vector in order and calls addTask. It is more readable than a classic index loop.
The syntax: for (const std::string& t : titles) { addTask(tasks, t); }. Here t takes one title each iteration; const and & pass it copy-free and read-only. This is the readable and efficient way modern C++ walks a range.
Exercise The runMenu function
Define void runMenu(std::vector<Task>& tasks, const std::vector<std::string>& titles). In the body, use a range-based for to call addTask(tasks, t) for each title. In main, declare std::vector<std::string> titles = {"Ekmek al", "Süt al", "Yumurta al"};, then call runMenu(tasks, titles) and listTasks(tasks).
Show example solution
#include <iostream>
#include <string>
#include <vector>
struct Task {
std::string title;
bool done;
};
void addTask(std::vector<Task>& tasks, const std::string& title) {
Task t;
t.title = title;
t.done = false;
tasks.push_back(t);
}
void listTasks(const std::vector<Task>& tasks) {
for (size_t i = 0; i < tasks.size(); ++i) {
if (tasks[i].done) {
std::cout << "[x] " << tasks[i].title << "\n";
} else {
std::cout << "[ ] " << tasks[i].title << "\n";
}
}
}
void completeTask(std::vector<Task>& tasks, size_t index) {
if (index < tasks.size()) {
tasks[index].done = true;
}
}
void runMenu(std::vector<Task>& tasks, const std::vector<std::string>& titles) {
for (const std::string& t : titles) {
addTask(tasks, t);
}
}
int main() {
std::vector<Task> tasks;
std::vector<std::string> titles = {"Ekmek al", "Süt al", "Yumurta al"};
runMenu(tasks, titles);
listTasks(tasks);
return 0;
}
Test yourself
-
What is the first line of runMenu output?
std::vector<Task> tasks;
std::vector<std::string> titles = {"Ekmek al", "Süt al", "Yumurta al"};
runMenu(tasks, titles);
listTasks(tasks);
- 1. Ekmek al
- Ekmek al
- [x] Ekmek al
- [ ] Ekmek al
Show answer
[ ] Ekmek al — The first task is not done yet, so '[ ] Ekmek al' is printed.
-
Match each expression to its meaning
- void runMenu
- Function signature
- for (const std::string& t : titles)
- Range-for
- addTask(tasks, t)
- Add call
- runMenu(tasks, titles)
- Call
-
runMenu body
for (const std::string& t : ____) { addTask(tasks, t); }
Show answer
for (const std::string& t : titles) { addTask(tasks, t); }
Next lesson: String streams