Cleanest way to write retry logic?

前端 未结 29 2480
旧巷少年郎
旧巷少年郎 2020-11-22 03:01

Occasionally I have a need to retry an operation several times before giving up. My code is like:

int retries = 3;
while(true) {
  try {
    DoSomething();
         


        
29条回答
  •  囚心锁ツ
    2020-11-22 03:34

    I'd implement this:

    public static bool Retry(int maxRetries, Func method)
    {
        while (maxRetries > 0)
        {
            if (method(maxRetries == 1))
            {
                return true;
            }
            maxRetries--;
        }
        return false;        
    }
    

    I wouldn't use exceptions the way they're used in the other examples. It seems to me that if we're expecting the possibility that a method won't succeed, its failure isn't an exception. So the method I'm calling should return true if it succeeded, and false if it failed.

    Why is it a Func and not just a Func? So that if I want a method to be able to throw an exception on failure, I have a way of informing it that this is the last try.

    So I might use it with code like:

    Retry(5, delegate(bool lastIteration)
       {
           // do stuff
           if (!succeeded && lastIteration)
           {
              throw new InvalidOperationException(...)
           }
           return succeeded;
       });
    

    or

    if (!Retry(5, delegate(bool lastIteration)
       {
           // do stuff
           return succeeded;
       }))
    {
       Console.WriteLine("Well, that didn't work.");
    }
    

    If passing a parameter that the method doesn't use proves to be awkward, it's trivial to implement an overload of Retry that just takes a Func as well.

提交回复
热议问题