C++ 创建计时器以在X秒内调用函数

C++ 创建计时器以在X秒内调用函数,c++,c++11,timer,C++,C++11,Timer,所以我有一个打印函数,我想在5秒内执行。问题是我需要函数中的所有其他内容。例如,如果我的代码是: // insert code here... printf("(5 seconds later) Hello"); /* should be executed in 5 seconds */ printf("heya"); 例如,在main函数中。现在是棘手的部分。虽然第一行应该在5秒内执行,但如果第一行根本不存在,第二行应该像正常情况一样执行。因此,输出将是: heya (5 seconds l

所以我有一个打印函数,我想在5秒内执行。问题是我需要函数中的所有其他内容。例如,如果我的代码是:

// insert code here...
printf("(5 seconds later) Hello"); /* should be executed in 5 seconds */
printf("heya");
例如,在main函数中。现在是棘手的部分。虽然第一行应该在5秒内执行,但如果第一行根本不存在,第二行应该像正常情况一样执行。因此,输出将是:

heya
(5 seconds later) Hello
如果您熟悉Cocoa或Cocoa Touch,这正是NSTimer类的工作方式。使用C++,除了使用线程之外,还有更简单的或内置的方式吗?如果没有,我将如何使用多线程来实现这一点

使用
,您可以创建一个非常基本但简单的:

std::thread printLater{[] {
    std::this_thread::sleep_for(std::chrono::seconds(5));
    printf("(5 seconds later) Hello");
}};

printf("heya");

printLater.join(); //when you want to wait for the thread to complete
Pubby指出的另一种方法是使用
std::async
:

auto f = std::async(std::launch::async, [] {
    std::this_thread::sleep_for(std::chrono::seconds(5));
    printf("(5 seconds later) Hello");
});

printf("heya");
std::async
存储到变量中的结果意味着调用将启动一个新线程来运行函数。如果不存储结果,则没有新线程。这是语言中的一个新的陷阱

请注意,打印时可能不超过5秒,并且没有同步输出,因此如果在每个线程中打印多个内容,则可能会得到交错的输出块(
printf
是原子的,因此每个调用的整个输出都会交错)。如果没有同步,就无法保证何时发生哪些语句,因此如果确实需要了解可能出现的同步问题,则应小心。不过,出于基本目的,这应该是可行的。

使用
,您可以创建一个非常基本但简单的:

std::thread printLater{[] {
    std::this_thread::sleep_for(std::chrono::seconds(5));
    printf("(5 seconds later) Hello");
}};

printf("heya");

printLater.join(); //when you want to wait for the thread to complete
Pubby指出的另一种方法是使用
std::async
:

auto f = std::async(std::launch::async, [] {
    std::this_thread::sleep_for(std::chrono::seconds(5));
    printf("(5 seconds later) Hello");
});

printf("heya");
std::async
存储到变量中的结果意味着调用将启动一个新线程来运行函数。如果不存储结果,则没有新线程。这是语言中的一个新的陷阱


请注意,打印时可能不超过5秒,并且没有同步输出,因此如果在每个线程中打印多个内容,则可能会得到交错的输出块(
printf
是原子的,因此每个调用的整个输出都会交错)。如果没有同步,就无法保证何时发生哪些语句,因此如果确实需要了解可能出现的同步问题,则应小心。不过,出于基本目的,这应该是可行的。

以下是我解决此问题的方法:

#include <iostream>
#include <thread>
#include <chrono>

std::thread timerThread;

void printStatement() {
    std::this_thread::sleep_for(std::chrono::seconds(5));
    printf("(5 seconds later) Hello");
}

bool myBool() {
    timerThread = std::thread(printStatement);
    return YES;
}


int main(int argc, const char * argv[])
{
    // insert code here...
    printf("%i\n", myBool());
    printf("heya\n");
    // you could also use the async stuff, join or std::future instead of sleep()
    sleep(5); // this is only here to keep the thread from being detatched before it can even finish sleeping
    timerThread.detach();
    return 0;
}
#包括
#包括
#包括
线程时间读取;
void printStatement(){
std::this_thread::sleep_for(std::chrono::seconds(5));
printf(“5秒后)你好”);
}
bool myBool(){
timerThread=std::thread(打印语句);
返回YES;
}
int main(int argc,const char*argv[]
{
//在这里插入代码。。。
printf(“%i\n”,myBool());
printf(“heya\n”);
//您还可以使用异步的东西join或std::future来代替sleep()
sleep(5);//这只是为了防止线程在完成睡眠之前被删除
timerThread.detach();
返回0;
}

以下是我解决此问题的方法:

#include <iostream>
#include <thread>
#include <chrono>

std::thread timerThread;

void printStatement() {
    std::this_thread::sleep_for(std::chrono::seconds(5));
    printf("(5 seconds later) Hello");
}

bool myBool() {
    timerThread = std::thread(printStatement);
    return YES;
}


int main(int argc, const char * argv[])
{
    // insert code here...
    printf("%i\n", myBool());
    printf("heya\n");
    // you could also use the async stuff, join or std::future instead of sleep()
    sleep(5); // this is only here to keep the thread from being detatched before it can even finish sleeping
    timerThread.detach();
    return 0;
}
#包括
#包括
#包括
线程时间读取;
void printStatement(){
std::this_thread::sleep_for(std::chrono::seconds(5));
printf(“5秒后)你好”);
}
bool myBool(){
timerThread=std::thread(打印语句);
返回YES;
}
int main(int argc,const char*argv[]
{
//在这里插入代码。。。
printf(“%i\n”,myBool());
printf(“heya\n”);
//您还可以使用异步的东西join或std::future来代替sleep()
sleep(5);//这只是为了防止线程在完成睡眠之前被删除
timerThread.detach();
返回0;
}

我的snap版本,带有boost asio和std::async。不允许睡觉

#include <boost/asio.hpp>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/noncopyable.hpp>

#include <chrono>
#include <future>
#include <memory>
#include <iostream>

class MonotonicExecutor
    : public boost::noncopyable,
      public std::enable_shared_from_this<MonotonicExecutor> {
  typedef std::function<void()> Functor;

public:
  MonotonicExecutor(boost::posix_time::time_duration trig)
      : m_service(),
        m_serviceWork(
            std::make_shared<boost::asio::io_service::work>(m_service)),
        m_deadlineTimer(m_service), m_trigger(trig) {
    auto fut = std::async(std::launch::async, [&]() { m_service.run(); });
    fut.wait_for(std::chrono::milliseconds(1));
  }
  void executeAsync(Functor fun) {
    m_deadlineTimer.expires_from_now(m_trigger);
    m_deadlineTimer.async_wait(std::bind(&MonotonicExecutor::execute,
                                         shared_from_this(),
                                         std::placeholders::_1, fun));
  }
  void abort() { m_deadlineTimer.cancel(); }

private:
  void execute(const boost::system::error_code &err, Functor fun) {
    if (err != boost::asio::error::operation_aborted &&
        m_deadlineTimer.expires_at() <=
            boost::asio::deadline_timer::traits_type::now()) {
      m_deadlineTimer.cancel();
      fun();
      m_deadlineTimer.expires_from_now(m_trigger);
      m_deadlineTimer.async_wait(std::bind(&MonotonicExecutor::execute,
                                           shared_from_this(),
                                           std::placeholders::_1, fun));
    }
  }

private:
  boost::asio::io_service m_service;
  std::shared_ptr<boost::asio::io_service::work> m_serviceWork;
  boost::asio::deadline_timer m_deadlineTimer;
  boost::posix_time::time_duration m_trigger;
};

int main(int argc, char *argv[]) {
  auto executor =
      std::make_shared<MonotonicExecutor>(boost::posix_time::seconds(3));
  executor->executeAsync([&]() {
    std::cout << boost::posix_time::to_iso_string(
                     boost::posix_time::second_clock::local_time())
              << std::endl;
  });

  auto stop = std::chrono::system_clock::now() + std::chrono::seconds(30);
  while (std::chrono::system_clock::now() < stop) {
    std::this_thread::sleep_for(std::chrono::seconds(1));
  }
  executor->abort();
  std::cout << "Wait and see if the task is aborted" << std::endl;
  stop = std::chrono::system_clock::now() + std::chrono::seconds(30);
  while (std::chrono::system_clock::now() < stop) {
    std::this_thread::sleep_for(std::chrono::seconds(1));
  }
  return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
类单调执行器
:public boost::不可复制,
public std::从此\u启用\u共享\u{
typedef std::函数函子;
公众:
单调执行器(boost::posix_time::time_duration trig)
:m_service(),
m_服务工作(
std::使_共享(m_服务)),
m_死线计时器(m_服务)、m_触发器(触发器){
auto-fut=std::async(std::launch::async,[&](){m_service.run();});
进一步等待(std::chrono::毫秒(1));
}
void executesync(函子fun){
m_deadlineTimer.expires_from_now(m_触发器);
m_deadlineTimer.async_wait(std::bind(&MonotonicExecutor::execute),
从_this()共享了_,
std::占位符::_1,fun));
}
void abort(){m_deadlineTimer.cancel();}
私人:
void execute(const boost::system::error\u code&err,Functor fun){
if(err!=boost::asio::error::operation\u中止&&
m_deadlineTimer.expires_at()executeAsync([&](){

std::cout我的snap版本,带有boost asio和std::async。不使用睡眠

#include <boost/asio.hpp>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/noncopyable.hpp>

#include <chrono>
#include <future>
#include <memory>
#include <iostream>

class MonotonicExecutor
    : public boost::noncopyable,
      public std::enable_shared_from_this<MonotonicExecutor> {
  typedef std::function<void()> Functor;

public:
  MonotonicExecutor(boost::posix_time::time_duration trig)
      : m_service(),
        m_serviceWork(
            std::make_shared<boost::asio::io_service::work>(m_service)),
        m_deadlineTimer(m_service), m_trigger(trig) {
    auto fut = std::async(std::launch::async, [&]() { m_service.run(); });
    fut.wait_for(std::chrono::milliseconds(1));
  }
  void executeAsync(Functor fun) {
    m_deadlineTimer.expires_from_now(m_trigger);
    m_deadlineTimer.async_wait(std::bind(&MonotonicExecutor::execute,
                                         shared_from_this(),
                                         std::placeholders::_1, fun));
  }
  void abort() { m_deadlineTimer.cancel(); }

private:
  void execute(const boost::system::error_code &err, Functor fun) {
    if (err != boost::asio::error::operation_aborted &&
        m_deadlineTimer.expires_at() <=
            boost::asio::deadline_timer::traits_type::now()) {
      m_deadlineTimer.cancel();
      fun();
      m_deadlineTimer.expires_from_now(m_trigger);
      m_deadlineTimer.async_wait(std::bind(&MonotonicExecutor::execute,
                                           shared_from_this(),
                                           std::placeholders::_1, fun));
    }
  }

private:
  boost::asio::io_service m_service;
  std::shared_ptr<boost::asio::io_service::work> m_serviceWork;
  boost::asio::deadline_timer m_deadlineTimer;
  boost::posix_time::time_duration m_trigger;
};

int main(int argc, char *argv[]) {
  auto executor =
      std::make_shared<MonotonicExecutor>(boost::posix_time::seconds(3));
  executor->executeAsync([&]() {
    std::cout << boost::posix_time::to_iso_string(
                     boost::posix_time::second_clock::local_time())
              << std::endl;
  });

  auto stop = std::chrono::system_clock::now() + std::chrono::seconds(30);
  while (std::chrono::system_clock::now() < stop) {
    std::this_thread::sleep_for(std::chrono::seconds(1));
  }
  executor->abort();
  std::cout << "Wait and see if the task is aborted" << std::endl;
  stop = std::chrono::system_clock::now() + std::chrono::seconds(30);
  while (std::chrono::system_clock::now() < stop) {
    std::this_thread::sleep_for(std::chrono::seconds(1));
  }
  return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
类单调执行器
:public boost::不可复制,
public std::从此\u启用\u共享\u{
typedef std::函数函子;
公众:
单调执行器(boost::posix_time::time_duration trig)
:m_service(),
m_服务工作(
std::使_共享(m_服务)),
m_死线计时器(m_服务)、m_触发器(触发器){
auto-fut=std::async(std::launch::async,[&](){m_service.run();});
进一步等待(std::chrono::毫秒(1));
}
void executesync(函子fun){
m_deadlineTimer.expires_from_now(m_触发器);
死线计时器。异步等待(标准: