I'm writing a project, and the part I'm doing now is getting bloated real fast. How can I remove this nested if
statements, but still have the same behaviour?
It would be nice the the resulting code was succinct, and extra local flags weren't required. This might not look so bad now, but I'm planning on writing more methods, up to T16
, you can imagine how bad these nested if
statements will get.
using ContainerExpressions.Containers;
using System;
namespace ContainerExpressions.Expressions.Core
{
internal static class Compose
{
public static Response<T> Evaluate<T>(Func<Response<T>> func) => func();
public static Response<TResult> Evaluate<T1, TResult>(Func<Response<T1>> func1, Func<T1, Response<TResult>> funcResult)
{
var response = new Response<TResult>();
var result = func1();
if (result)
{
response = response.WithValue(funcResult(result));
}
return response;
}
public static Response<TResult> Evaluate<T1, T2, TResult>(Func<Response<T1>> func1, Func<T1, Response<T2>> func2, Func<T2, Response<TResult>> funcResult)
{
var response = new Response<TResult>();
var result1 = func1();
if (result1)
{
var result2 = func2(result1);
if (result2)
{
response = response.WithValue(funcResult(result2));
}
}
return response;
}
public static Response<TResult> Evaluate<T1, T2, T3, TResult>(Func<Response<T1>> func1, Func<T1, Response<T2>> func2, Func<T2, Response<T3>> func3, Func<T3, Response<TResult>> funcResult)
{
var response = new Response<TResult>();
var result1 = func1();
if (result1)
{
var result2 = func2(result1);
if (result2)
{
var result3 = func3(result2);
if (result3)
{
response = response.WithValue(funcResult(result3));
}
}
}
return response;
}
}
}
1 Answer 1
If your code will always behave as the parts shown, you can refactor it to early-out returns. I show your Evaluate<T1, T2, T3, TResult>(...)
as an example:
public static Response<TResult> Evaluate<T1, T2, T3, TResult>(Func<Response<T1>> func1, Func<T1, Response<T2>> func2, Func<T2, Response<T3>> func3, Func<T3, Response<TResult>> funcResult)
{
var response = new Response<TResult>();
if (!func1()) return response;
if (!func2(true)) return response;
if (!func3(true)) return response;
return response.WithValue(funcResult(result3));
}
So you get rid of the nesting if
statements. And you don't need the local flag variables since you know that the value is true
.
-
\$\begingroup\$ "reducing bloat" is a good thing but it is also subjective, I'll know it when I see it kind of thing; this "early out" technique objectively reduces complexity - a software engineering term of art . You can put a number on "complexity" using software analysis tools. And from this fine answer we can intuitively see complexity management positively affects other code quality aspects. Learn about software complexity per se and you simultaneously deal with many "mushy" issues on CodeReview posts featured as the primary problem. \$\endgroup\$radarbob– radarbob2024年10月11日 17:31:21 +00:00Commented Oct 11, 2024 at 17:31