草庐IT

c - 如何定义要运行几秒/分钟的循环

coder 2023-06-19 原文

我的目的是在定义的时间内执行 while 循环(例如,本例中为 90 秒)。它不必正好是 90 秒,但 1-2 秒的误差是可以接受的。为此,我确实使用了 clock()` 函数:

int main(void){
      clock_t start, end;
      volatile double elapsed;
      start = clock();
      int terminate = 1;
      while(terminate)
      {
              end = clock();
              elapsed = ((double) (end-start)) / (double) CLOCKS_PER_SEC *1000;
              printf("elapsed time:%f\n",elapsed);
              if(elapsed >= 90.0)
                        terminate = 0;
               usleep(50000);
       }
      printf("done..\n");
    return 0;
}

当我在我的笔记本电脑(x86、3.13 内核、gcc 4.8.2)上运行它时,我的秒表显示它完成了 72 秒。 (1000 是我笔记本电脑上 elapsed 秒级精度所必需的)

当我在 ARM 设备(armv5tejl、3.12 内核、gcc 4.6.3)上运行它时,完成代码需要 58 秒。 (我需要在 armv5 上的 elapsed 上使用 100)。

我在室温下运行代码,因此时钟应该稳定。我知道内核使线程休眠并且唤醒它们的时间不准确,等等。因此,正如我之前所说,我不希望获得完美的时间,但它应该有一定的准确性。

我曾尝试仅使用 usleep(甚至是 nanosleep),但分辨率也不是很好。最后我想出了获取系统时间(小时、分钟、秒)然后计算耗时的底部代码。它的工作精度很高。

我想知道是否有另一种使用成本更低的解决方案?

typedef struct{
    int hour;
    int minute;
    int second;
} timeInfo;

timeInfo getTimeInfo(void){
    timeInfo value2return;
    time_t rawtime;
    struct tm * timeinfo;
    time(&rawtime);
    timeinfo = localtime(&rawtime);
    value2return.hour = timeinfo->tm_hour;
    value2return.minute = timeinfo->tm_min;
    value2return.second = timeinfo->tm_sec;
    return value2return;
}

int checkElapsedTime(const timeInfo *Start, const timeInfo *Stop, const int Reference){
    if(Stop->hour < Start->hour){
        printf("1:%d\n", (Stop->hour +24) *3600 + Stop->minute *60 + Stop->second - (Start->hour *3600 +Start->minute * 60 + Start->second));
         if( ( (Stop->hour +24) *3600 + Stop->minute *60 + Stop->second - (Start->hour *3600 +Start->minute * 60 + Start->second)) >= Reference )
            return 0; //while(0): terminate the loop
         else
             return 1; //while(1)
    }else{
        printf("2:%d\n",Stop->hour *3600 + Stop->minute *60 + Stop->second - (Start->hour *3600 +Start->minute * 60 + Start->second));
        if( (Stop->hour *3600 + Stop->minute *60 + Stop->second - (Start->hour *3600 +Start->minute * 60 + Start->second)) >= Reference )
            return 0;
        else
            return 1;
    }
}

int main(void){

    timeInfo stop, start = getTimeInfo();
    int terminate = 1;
    while(terminate)
    {
        stop = getTimeInfo();
        terminate = checkElapsedTime(&start, &stop, 90);
        usleep(5000); //to decrease the CPU load
    }

    printf("terminated\n");

    return 0;
}

最后,我需要在 pthread 中运行它。

最佳答案

  1. 使用 time()clock()。编码目标是确定经过的墙时间而不是使用的处理器时间。

    当前代码计算了经过的进程时间 * 1000 并将其与 90 秒进行比较。

    clock(),@uesp 暗示,返回“时钟函数决定使用的处理器时间。” C11dr §7.27.2.1 2.

    time() 返回“时间函数确定当前日历时间”§7.27.2.4 2

    difftime() 可以很好地找到 2 个 time_t 之间的差异(无论它们是什么单位/类型)并以秒为单位返回差异。

    int main(void) {
       time_t start, end;
       double elapsed;  // seconds
       start = time(NULL);
       int terminate = 1;
       while (terminate) {
         end = time(NULL);
         elapsed = difftime(end, start);
         if (elapsed >= 90.0 /* seconds */)
           terminate = 0;
         else  // No need to sleep when 90.0 seconds elapsed.
           usleep(50000);
       }
       printf("done..\n");
       return 0;
     }
    
  2. 次要:注意:使用clock()时,不需要* 1000。在运行 gcc 的基于 Windows 的机器上,对我来说,clock() 还返回了调用进程的 CPU 时间。

    elapsed = ((double) (end-start)) / (double) CLOCKS_PER_SEC *1000;
    elapsed = ((double) (end-start)) / CLOCKS_PER_SEC;
    
  3. 次要:不需要 volatileelapsed 仅由于此代码而发生变化。

    // volatile double elapsed;
    double elapsed;
    

关于c - 如何定义要运行几秒/分钟的循环,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25475835/

有关c - 如何定义要运行几秒/分钟的循环的更多相关文章

  1. ruby - 如何使用 Nokogiri 的 xpath 和 at_xpath 方法 - 2

    我正在学习如何使用Nokogiri,根据这段代码我遇到了一些问题:require'rubygems'require'mechanize'post_agent=WWW::Mechanize.newpost_page=post_agent.get('http://www.vbulletin.org/forum/showthread.php?t=230708')puts"\nabsolutepathwithtbodygivesnil"putspost_page.parser.xpath('/html/body/div/div/div/div/div/table/tbody/tr/td/div

  2. ruby - 如何从 ruby​​ 中的字符串运行任意对象方法? - 2

    总的来说,我对ruby​​还比较陌生,我正在为我正在创建的对象编写一些rspec测试用例。许多测试用例都非常基础,我只是想确保正确填充和返回值。我想知道是否有办法使用循环结构来执行此操作。不必为我要测试的每个方法都设置一个assertEquals。例如:describeitem,"TestingtheItem"doit"willhaveanullvaluetostart"doitem=Item.new#HereIcoulddotheitem.name.shouldbe_nil#thenIcoulddoitem.category.shouldbe_nilendend但我想要一些方法来使用

  3. ruby - Facter::Util::Uptime:Module 的未定义方法 get_uptime (NoMethodError) - 2

    我正在尝试设置一个puppet节点,但ruby​​gems似乎不正常。如果我通过它自己的二进制文件(/usr/lib/ruby/gems/1.8/gems/facter-1.5.8/bin/facter)在cli上运行facter,它工作正常,但如果我通过由ruby​​gems(/usr/bin/facter)安装的二进制文件,它抛出:/usr/lib/ruby/1.8/facter/uptime.rb:11:undefinedmethod`get_uptime'forFacter::Util::Uptime:Module(NoMethodError)from/usr/lib/ruby

  4. python - 如何使用 Ruby 或 Python 创建一系列高音调和低音调的蜂鸣声? - 2

    关闭。这个问题是opinion-based.它目前不接受答案。想要改进这个问题?更新问题,以便editingthispost可以用事实和引用来回答它.关闭4年前。Improvethisquestion我想在固定时间创建一系列低音和高音调的哔哔声。例如:在150毫秒时发出高音调的蜂鸣声在151毫秒时发出低音调的蜂鸣声200毫秒时发出低音调的蜂鸣声250毫秒的高音调蜂鸣声有没有办法在Ruby或Python中做到这一点?我真的不在乎输出编码是什么(.wav、.mp3、.ogg等等),但我确实想创建一个输出文件。

  5. ruby-on-rails - 如何验证 update_all 是否实际在 Rails 中更新 - 2

    给定这段代码defcreate@upgrades=User.update_all(["role=?","upgraded"],:id=>params[:upgrade])redirect_toadmin_upgrades_path,:notice=>"Successfullyupgradeduser."end我如何在该操作中实际验证它们是否已保存或未重定向到适当的页面和消息? 最佳答案 在Rails3中,update_all不返回任何有意义的信息,除了已更新的记录数(这可能取决于您的DBMS是否返回该信息)。http://ar.ru

  6. ruby-on-rails - 'compass watch' 是如何工作的/它是如何与 rails 一起使用的 - 2

    我在我的项目目录中完成了compasscreate.和compassinitrails。几个问题:我已将我的.sass文件放在public/stylesheets中。这是放置它们的正确位置吗?当我运行compasswatch时,它不会自动编译这些.sass文件。我必须手动指定文件:compasswatchpublic/stylesheets/myfile.sass等。如何让它自动运行?文件ie.css、print.css和screen.css已放在stylesheets/compiled。如何在编译后不让它们重新出现的情况下删除它们?我自己编译的.sass文件编译成compiled/t

  7. ruby - 树顶语法无限循环 - 2

    我脑子里浮现出一些关于一种新编程语言的想法,所以我想我会尝试实现它。一位friend建议我尝试使用Treetop(Rubygem)来创建一个解析器。Treetop的文档很少,我以前从未做过这种事情。我的解析器表现得好像有一个无限循环,但没有堆栈跟踪;事实证明很难追踪到。有人可以指出入门级解析/AST指南的方向吗?我真的需要一些列出规则、常见用法等的东西来使用像Treetop这样的工具。我的语法分析器在GitHub上,以防有人希望帮助我改进它。class{initialize=lambda(name){receiver.name=name}greet=lambda{IO.puts("He

  8. ruby-on-rails - 在 Ruby 中循环遍历多个数组 - 2

    我有多个ActiveRecord子类Item的实例数组,我需要根据最早的事件循环打印。在这种情况下,我需要打印付款和维护日期,如下所示:ItemAmaintenancerequiredin5daysItemBpaymentrequiredin6daysItemApaymentrequiredin7daysItemBmaintenancerequiredin8days我目前有两个查询,用于查找maintenance和payment项目(非排他性查询),并输出如下内容:paymentrequiredin...maintenancerequiredin...有什么方法可以改善上述(丑陋的)代

  9. ruby - 如何将脚本文件的末尾读取为数据文件(Perl 或任何其他语言) - 2

    我正在寻找执行以下操作的正确语法(在Perl、Shell或Ruby中):#variabletoaccessthedatalinesappendedasafileEND_OF_SCRIPT_MARKERrawdatastartshereanditcontinues. 最佳答案 Perl用__DATA__做这个:#!/usr/bin/perlusestrict;usewarnings;while(){print;}__DATA__Texttoprintgoeshere 关于ruby-如何将脚

  10. ruby - 如何指定 Rack 处理程序 - 2

    Rackup通过Rack的默认处理程序成功运行任何Rack应用程序。例如:classRackAppdefcall(environment)['200',{'Content-Type'=>'text/html'},["Helloworld"]]endendrunRackApp.new但是当最后一行更改为使用Rack的内置CGI处理程序时,rackup给出“NoMethodErrorat/undefinedmethod`call'fornil:NilClass”:Rack::Handler::CGI.runRackApp.newRack的其他内置处理程序也提出了同样的反对意见。例如Rack

随机推荐