如何在特定时间后终止递归函数?

时间:2013-11-06 00:14:56

标签: c++ c ubuntu recursion

我在C ++中有一个递归函数,我需要立即终止函数,包括在特定时间后递归发出的所有调用,比如60秒。 我尝试了以下但不起作用。 takesTooLong是一个全局变量,但如果它的值在一次调用中变为1,则其他调用会将其视为0。 操作系统 Ubuntu 12.10

main()是这样的:

int main()
{
    takesTooLong = 0;
    startTime = clock();
    RecursiveFunction();
    endTime = clock();
    printf("Elapsed time: %f", CalculateElapsedTime(startTime, endTime));
    return 0;
}

我的递归函数:

void RecursiveFunction(Some Parameters)
{
    if (takesTooLong == 1)
        return;

    endTime = clock();
    differenceTime = CalculateElapsedTime(startTime, endTime);
    if (differenceTime > MAX_SECONDS)
    {
        takesTooLong = 1;
    }

    if (takesTooLong == 0)
    {
        for (i = 0; i < n && takesTooLong == 0; i++)
        {
            RecursiveFunction(Some Updated Parameters);
        }
    }   
}

3 个答案:

答案 0 :(得分:0)

伪代码:

typedef ??? Time;//time type
Time getCurrentTime(); //returns time. Or ticks. Anything you could use to measure time.

void recursiveFunction(Time startTime){       
    ...//do something here
    Time currentTime = getCurrentTime();                
    if ((currentTime - startTime) > limit)
        return;
    recursiveFunction(startTime);
}

void recursiveFunction(){
     Time startTime = getCurrentTime();
     recursiveFunction(startTime);
}  

答案 1 :(得分:0)

是的,你仍然必须展开堆栈,但替代方案都很难看,最好的可能是longjmp。如果您需要更高的分辨率而不是秒,或者您想测量进程/内核时间而不是挂钟时间,请使用timer_createsetitimer等替代方案。

void alarmHandler (int sig)
{
    timedOut = 1;
}


    signal(SIGALRM, alarmHandler);

    alarm(60);
    RecursiveFunction();
    alarm(0);

    if (timedOut)
    {
        //report something
        timedOut = 0;
    }


void RecursiveFunction(Some Parameters)
{
    if (timedOut)
        return;

    //........
}

答案 2 :(得分:0)

退出未知数量的递归的最简单方法是抛出异常。由于你每60秒最多做一次,所以这并不算太糟糕。只需将其设为class TimeLimitExceeded : public std::runtime_error并在顶级包装器中捕获†。

†大多数递归函数不应该直接调用,而是通过非递归包装器调用。递归函数的签名通常对于调用者来说是不方便的,因为它包含与调用者无关的实现细节。