C# с использованием рекурсии только с одним возвратом
У меня есть следующая рекурсивная функция
public int Factorial(int number_to_calculate)
{
if (StackChanged != null)
{
StackChanged(new CustomEventArgs(StackValue, Result));
}
System.Threading.Thread.Sleep(wait_time);
if (number_to_calculate == 0)
{
StackValue--;
return 1;
}
else
{
StackValue++;
Result = (number_to_calculate * Factorial(number_to_calculate - 1));
}
if (StackChanged != null)
{
StackChanged(new CustomEventArgs(StackValue, Result));
}
StackValue--;
System.Threading.Thread.Sleep(wait_time);
return Result;
}
По-видимому, мой супервизор не согласен с тем, что у меня 2 возврата, но хочет, чтобы функция была рекурсивной. Так что мне нужно только одно возвращение. Я уже пытался использовать аккумулятор с началом goto, чтобы получить только один возврат, но мне нужно увеличивать StackValue каждый раз, когда функция вызывает себя, и уменьшать его, когда она выходит из рекурсии. Таким образом, я не буду знать, когда он выйдет.
У кого-нибудь есть какие-либо идеи?
3 ответа
Вместо
if (number_to_calculate == 0)
{
StackValue--;
return 1;
}...
делать
if (number_to_calculate == 0)
{
result = 1;
}
Самый простой способ сделать функцию с одним оператором return - сохранить значение, которое нужно вернуть, в переменной, а затем вернуть его в конце. Таким образом, вы должны преобразовать что-то вроде следующего:
int myFunc() {
if (cond)
return x;
else
return y;
}
На что-то вроде этого:
int myFunc() {
int returnValue;
if (cond)
returnValue = x;
else
returnValue = y;
return returnValue;
}
Этот принцип может быть применен в целом к любому методу, если вы позаботитесь о том, чтобы при изменении оператора возврата на присвоение переменной у вас была настройка условий, поэтому остальная часть кода будет пропущена.
Однако подобное требование довольно произвольно. В общем случае ожидается, что с рекурсией будет несколько операторов return.
int Factorial(int number)
{
int result = 1;
StackValue++;
if (StackChanged != null)
StackChanged(new CustomEventArgs(StackValue, Result));
if (number > 1)
{
System.Threading.Thread.Sleep(wait_time);
result = number * Factorial(number - 1);
}
StackValue--;
if (StackChanged != null)
StackChanged(new CustomEventArgs(StackValue, Result));
return result;
}