- 1. Projektstruktur
- 2. CMakeLists.txt
- 3. PeriodicTask.h
- 4. PeriodicTask.cpp
- 5. main.cpp
- 6. Fazit
Ich schlage vor, ein kleines Konsolenprogramm zu schreiben, das in regelmäßigen Abständen eine Aufgabe ausführt.
Beispielsweise startet das Programm und macht 10 Proben innerhalb von 10 Sekunden, während das Programm Informationen über die Anzahl der Countdowns in der Konsole anzeigt.
Das Programm wird wie folgt funktionieren.
Projektstruktur
Das Projekt verwendet das CMake-Buildsystem, daher sieht die Projektstruktur wie folgt aus.
CMakeLists.txt
Hier ist die CMake-Standardkonfiguration zum Erstellen eines Projekts.
cmake_minimum_required (VERSION 3.8) project(Periodic) set(CMAKE_CXX_STANDARD 17) set(Boost_USE_STATIC_LIBS ON) find_package(Boost 1.68 REQUIRED COMPONENTS thread) set(SOURCE_FILES Periodic/main.cpp Periodic/PeriodicTask.cpp) SET(HEADER_FILES Periodic/PeriodicTask.h) if(Boost_FOUND) include_directories(${Boost_INCLUDE_DIRS}) add_executable(Periodic ${SOURCE_FILES} ${HEADER_FILES}) target_link_libraries(Periodic ${Boost_LIBRARIES}) endif()
PeriodicTask.h
Die Header-Datei der periodischen Aufgabe.
Im einfachsten Fall benötigen wir zum Erstellen einer periodischen Aufgabenklasse:
- Auslöseperiode
- std::function-Objekt zum Speichern der Aufgabe
- bool-Variable zum Stoppen und Starten der Aufgabe. In diesem Beispiel werden wir die Aufgabe nicht stoppen, aber wenn wir run / stop-Methoden hinzufügen, ist es durchaus möglich, dies zu implementieren.
- boost::thread ist ein Thread, ohne den diese Funktionalität nicht implementiert werden kann
#pragma once #include <boost/thread.hpp> #include <boost/chrono.hpp> #include <functional> #include <atomic> class PeriodicTask { public: explicit PeriodicTask(const boost::chrono::milliseconds &period, const std::function<void()> &func); virtual ~PeriodicTask(); private: boost::chrono::milliseconds m_period; // Task period std::function<void()> m_func; // The function that will perform the periodic task std::atomic<bool> m_running; // A variable that indicates that the task is running, with the help of it you can stop the task in the future boost::thread m_thread; // Task thread };
PeriodicTask.cpp
#include "PeriodicTask.h" PeriodicTask::PeriodicTask(const boost::chrono::milliseconds &period, const std::function<void()> &func) : m_period(period), m_func(func), m_running(true) { // Create a stream object to perform a periodic task. m_thread = boost::thread([this] { while (m_running) { // To perform a task with a specific period, immerse the stream in a dream after each task execution. boost::this_thread::sleep_for(m_period); if (m_running) { // perform the task m_func(); } } }); } PeriodicTask::~PeriodicTask() { // When destroying an object with a periodic task m_running = false; // interrupt the flow, otherwise the program will not release system resources until the flow comes out of sleep // this is critical if the trigger period of the task is measured in tens of seconds and more m_thread.interrupt(); m_thread.join(); }
main.cpp
Datei mit Hauptfunktion. Wenn wir ein periodisches Aufgabenobjekt erstellen, fügen wir eine Lambda-Funktion als Aufgabe hinzu, um so am einfachsten anzugeben, welche Arbeit zu erledigen ist.
#include "PeriodicTask.h" // We connect the class header file to perform periodic tasks. #include <iostream> int main(int argc, const char* argv[]) { std::cout << "Start program" << std::endl; int count = 0; // Create a periodic task with a period of 1 second PeriodicTask p(boost::chrono::seconds{ 1 }, [&count]() { // Display the counter and increment it by one. std::cout << count++ << std::endl; }); // Stop the main program flow for 10 seconds so that the periodic task can work 10 times. boost::this_thread::sleep_for(boost::chrono::seconds{ 10 }); std::cout << "End program" << std::endl; return 0; }
Fazit
Abschließend lege ich dem Projekt das Archiv bei.