2012-06-26 9 views
22

सी ++ 11 में, *_until टाइमआउट फ़ंक्शंस केवल "अपेक्षित" व्यवहार करते हैं, यदि केवल एक स्थिर घड़ी (यानी, जो केवल एक अपरिवर्तनीय दर पर आगे बढ़ता है) का उपयोग किया जाता है। क्योंकि system_clock एक स्थिर घड़ी नहीं है, इसका मतलब है कि इस तरह से है कि कोड काफी आश्चर्यजनक रूप से व्यवहार करते हैं कर सकते हैं:संबंधित * _for फ़ंक्शन के बजाय सी ++ 11 * _until टाइमआउट फ़ंक्शन का उपयोग करना उचित कब है?

using namespace std::chrono; 
std::this_thread::sleep_until(system_clock::now() + seconds(10)); 

यह वर्तमान धागा 10 सेकंड के लिए सोने के लिए कारण होगा, जब तक कि सिस्टम घड़ी नींद की अवधि के दौरान निकाला जाता है, जैसे, डेलाइट बचत समय के लिए। अगर घड़ी नींद के दौरान एक घंटा वापस सेट की जाती है, तो वर्तमान धागा एक घंटे और 10 सेकंड तक सो जाएगा।

मैं जो कह सकता हूं, से प्रत्येक *_until सी ++ 11 में टाइमआउट फ़ंक्शन में *_for फ़ंक्शन है जो एक टाइमपॉइंट की बजाय अवधि लेता है। उदाहरण के लिए, इस प्रकार उपरोक्त कोड में लिखा जा सकता:

using namespace std::chrono; 
std::this_thread::sleep_for(seconds(10)); 

*_for काम करता है, घड़ियों है कि जब समारोह निष्पादित हो रहा है एडजस्ट हो जाते हैं के बारे में चिंता करने के लिए, क्योंकि वे सिर्फ कितनी देर तक प्रतीक्षा करने के लिए, यह नहीं कह नहीं होना चाहिए क्या जब प्रतीक्षा खत्म हो जाती है तो ऐसा लगता है।

यह समस्या नींद कार्यों से अधिक प्रभावित करती है, क्योंकि यह टाइमआउट-आधारित वायदा और try_lock कार्यों पर प्रतीक्षा करता है।

केवल स्थिति है जिसमें मैं यह कल्पना कर सकते हैं एक अस्थिर घड़ी के साथ एक *_until फ़ंक्शन का उपयोग किया जाएगा जब आप चाहते खाते में घड़ी समायोजन लेने के लिए, उदाहरण के लिए, आप 3 पर अगले बुधवार तक सोना चाहता हूँ अर्थ निकालने: 30AM, भले ही डेलाइट बचत समय में या उसके बीच में कोई बदलाव हो। क्या ऐसी अन्य स्थितियां हैं जहां *_until फ़ंक्शंस *_for फ़ंक्शंस से अधिक समझ में आता है? यदि नहीं, तो क्या यह कहना सुरक्षित है कि, सामान्यतः *_for टाइमआउट फ़ंक्शंस को *_until फ़ंक्शंस पर प्राथमिकता दी जानी चाहिए?

+0

क्या यह _clock_ की _steadiness_ पर निर्भर नहीं होगा? क्या 'wait_for' और 'wait_until' वास्तव में' घड़ी कूद 'के संचालन में अलग-अलग काम करने का इरादा रखते हैं? –

+0

@ के-बॉलो: ठीक है, यही कारण है कि मैंने विशेष रूप से घड़ी की स्थिरता का उल्लेख किया और वह system_clock स्थिर नहीं है। '_for' और' _until' फ़ंक्शंस घड़ी समायोजन के संबंध में अलग-अलग व्यवहार करते हैं, लेकिन _intention_ मुझे क्या स्पष्ट नहीं है। – KnowItAllWannabe

+1

'system_clock' का _steadiness_ वास्तव में कार्यान्वयन निर्भर है। –

उत्तर

9

xxx_until कॉल आपकी समय सीमा के लिए हैं। सामान्य उपयोग केस वह जगह है जहां आपके पास कोड के एक अनुभाग के लिए कठिन समय सीमा होती है जिसमें या तो कई प्रतीक्षा होती है, या जहां प्रतीक्षा से पहले प्रत्येक चरण द्वारा खपत का समय अप्रत्याशित होता है।

उदा।

void foo() { 
    std::chrono::steady_clock::time_point const timeout= 
    std::chrono::steady_clock::now()+std::chrono::milliseconds(30); 

    do_something_which_takes_some_time(); 

    if(some_future.wait_until(timeout)==std::future_status::ready) 
    do_something_with(some_future.get()); 
} 

यह केवल some_future से मूल्य पर कार्रवाई करेंगे अगर यह समय do_something_which_takes_some_time() के लिए ले जाया सहित शुरू, से 30ms के भीतर तैयार है।

इस उदाहरण के रूप में, xxx_until फ़ंक्शंस का सबसे अधिक उपयोग केस अनुमानित टाइमआउट करने के लिए एक स्थिर घड़ी का उपयोग करेंगे।

केवल इस मामले में जहां मैं एक गैर स्थिर घड़ी के साथ xxx_until कार्यों का उपयोग कर कल्पना कर सकते हैं (जैसे std::chrono::system_clock) जहां टाइमआउट उपयोगकर्ता के देखा जा सकता है, और चुने हुए घड़ी के मूल्य पर निर्भर करता है। अलार्म घड़ी या अनुस्मारक कार्यक्रम एक उदाहरण है, एक बैकअप प्रोग्राम जो "आधी रात को" चलाता है वह दूसरा है।

4

sleep_until फ़ंक्शन के लिए एक उपयोग-केस यह है कि यदि आप एक विशिष्ट समय तक सोना चाहते हैं, न कि विशिष्ट अवधि।

उदाहरण के लिए, यदि आप एक धागा है कि केवल हर दिन के 3 बजे को सक्रिय करना चाहिए है, तो आप या तो sleep_for साथ प्रयोग के लिए (दिन के उजाले से निपटने की बचत और लीप वर्ष सहित) अवधि की गणना करने के लिए है, या आप sleep_until इस्तेमाल कर सकते हैं।

+1

अलार्म घड़ी कुछ ऐसा उत्कृष्ट उदाहरण है जिसे डेलाइट सेविंग टाइम को ध्यान में रखना चाहिए। आपके कामकाजी घंटों को डीएसटी में समायोजित किया जाता है, और इसलिए आपकी अलार्म घड़ी भी होनी चाहिए। –

2

sleep_until के लिए एक अच्छा उपयोग स्थिर समय के लूप (जैसे गेम लूप) में है। यदि आप सुनिश्चित नहीं हैं कि एक चक्र प्रक्रिया में कितना समय लगेगा, लेकिन यह आमतौर पर एक निश्चित न्यूनतम लंबाई का होना चाहिए, तो आप चक्र अवधि तक समय-बिंदु को सोए जाने के लिए बढ़ा सकते हैं। उदाहरण के लिए:

// requires C++14 
#include <iostream> 
#include <thread> 
#include <chrono> 

using namespace std; 
using namespace std::chrono; 
using namespace std::literals; 

int main() 
{ 
    auto start_time = steady_clock::now(); 

    for (auto i = start_time; i <= start_time + 1s; i += 50ms) { 
    this_thread::sleep_until(i); 
    cout << "processing cycle..." << endl; 
    } 

    return 0; 
} 

लेकिन तब आप शायद अंतराल पर नज़र रखने के लिए जब एक चक्र वेतन वृद्धि समय की तुलना में लंबे समय तक लेता है मिल गया है।

विचार यह है कि, यदि आप sleep_for पर भरोसा करते हैं, तो आप अपने चक्र अवधि प्लस सोते समय आपके इन-लूप कोड को चलाने के लिए सोएंगे।

 संबंधित मुद्दे

  • कोई संबंधित समस्या नहीं^_^