#pragma once #include #include #include #include #include #include #include #include class Philosopher; typedef std::shared_ptr PhilosopherPtr; typedef std::vector ListOfPhilosophers; typedef std::shared_ptr ListOfPhilosophersPtr; extern std::mutex changingForkState; extern std::mutex printing; /** * \brief A class representing a single philosopher having his dinner. * * Philosophers are seated in a round table. * In order of being able to eat a philosopher should be able to take * the two forks on his sides so no other of its neighbor philosophers * should be eating at this time. */ class Philosopher { private: //! The position of the philosopher in the table. int numberOfPhilosopher; //! What the philosopher is doing. PhilosopherState state{PhilosopherState::THINKING}; //! The vector of philosophers in the table. ListOfPhilosophersPtr philosophers; //! The function to set the state of the philosopher. void setState(PhilosopherState state); //! Method to guess the numberOfPhilosopher of the left neighbor of this philosopher. size_t leftPhilosopherNumber(void); //! Method to guess the numberOfPhilosopher of the right neighbor of this philosopher. size_t rightPhilosopherNumber(void); //! Retrieve the left neighbor. PhilosopherPtr leftPhilosopher(void); //! Retrieve the right neighbor. PhilosopherPtr rightPhilosopher(void); //! Makes the philosopher think for a while. void think(void); //! The philosopher waits until the forks of his neighbors are free and then takes the two forks. void takeForks(void); //! The philosopher eats the spaghetti with the two forks. void eat(void); //! The philosopher puts the forks in the table to be used by his neighbors. void putForks(void); public: //! Retrieves the philosopher state. PhilosopherState getState(void); /** * \brief Philosopher constructor * @param philosophers The vector of in the table philosophers. * @param numberOfPhilosopher The position of this philosopher in the table. */ Philosopher(ListOfPhilosophersPtr philosophers, int numberOfPhilosopher); //! Whenever this philosopher was the two forks currently. std::binary_semaphore hasBothForks{0}; //! Starts the philosopher dinner. void startThread(void); //! Test if the philosopher should be able to take both forks currently. void test(void); };