0

I have a console Windows application written in C++ that finds a solution (or proves non-existance of solution) for a given level for some step-by-step game. Let's call it "solver". This application is launched in a loop from Python script for all game levels. Some levels are too difiicult and it takes hours ot even days to solve them.

It would be acceptable if my application could output some string, say "Too difficult level" and exit thus allowing to Python script to move onto the next level, if it has failed to find a solution (or to prove its inexistance) in, say, 30 minutes.

How do I interrupt the solver 30 seconds after it has started? Technically, solving algorithm is just a recursive procedure called from int main().

I am thinking over creating secondary thread that would wake up 30 minutes after being launched and set some boolean flag. And primiry (solving) thread would check this flag periodically.

This would work, but isn't there any simpler of more elegant solution?

Nick
  • 3,205
  • 9
  • 57
  • 108
  • you could also capture the start time using `std::chrono::system_clock::now()` and check the time difference in your loop. However, your proposed solution might be more economical. You have to take care of synchronization of the boolean value, though. – Dmitry Ledentsov Nov 13 '13 at 16:30
  • @DmitryLedentsov It's not synchronisation so much as dangers of erroneous caching. Any race would be benign. An atomic is what is needed. – David Heffernan Nov 13 '13 at 16:33
  • may duplicate with this:http://stackoverflow.com/questions/2128620/how-to-create-timer-in-winapi-c – Matt Nov 13 '13 at 16:40

2 Answers2

2

Since your code is not running in a message driven way, I'm not sure that a timer is needed here, or would even be appropriate. You are probably right that you need your main calculation thread to check periodically if it needs to timeout. In which case there's no need for another thread with a timer. Just remember the time when the calculation started, and every time you check for timeout, see if 30 seconds have elapsed.

In pseudocode:

startTime = now();
while (doingCalc)
{
    DoSomeMoreCalc();
    if (now() - startTime) > 30.0)
        timeOut();
}
David Heffernan
  • 601,492
  • 42
  • 1,072
  • 1,490
  • This is probably the best solution; since you're busy looping anyway there's no need for a timer, just check the time as part of the loop. – Jonathan Potter Nov 13 '13 at 20:54
0

Not sure if this will work but it's worth a shot..

#include <windows.h>
#include <iostream>
#include <thread>

UINT_PTR ID = NULL;

void __stdcall OnTimerEvent(HWND hwnd, UINT msg, UINT_PTR id, DWORD dwTime)
{
    std::cout<<"HERE\n";
    KillTimer(NULL, ID);
}

int main()
{
    std::thread([] {
        MSG msg = {0};
        ID = SetTimer(NULL, 0, 3000, &OnTimerEvent); //3 second timer.

        while(GetMessage(&msg, NULL, 0, 0))
        {
            DispatchMessage(&msg);
        }

        KillTimer(NULL, ID);
    }).detach();

    std::cin.get();
}
Brandon
  • 22,723
  • 11
  • 93
  • 186
  • 1
    -1 *"Console application"* and *`DispatchMessage`* have zero overlap. – IInspectable Nov 13 '13 at 18:44
  • 2
    I don't think you can read.. "WinAPI Timer for Console Application". That is exactly what I gave OP. Take a look at the tags again. It's tagged Winapi, Multi-Threading, Timer. My solution is not be the best but it has all of those and it works. – Brandon Nov 13 '13 at 19:56
  • 1
    The asker did not ask for a program that demonstrates how to call `SetTimer` in a thread. I think if anyone cannot read it is you. Read the question closely. Try and answer with more text and less code. – David Heffernan Nov 13 '13 at 20:56