I would do this a little differently...
/// <summary>
/// Uses <see cref="EqualityComparer{TValue}"/> to determine if <paramref name="left"/> is
/// equal to <paramref name="right"/>. If it is, <paramref name="returnIfEqual"/> is returned,
/// otherwise, <paramref name="returnIfNotEqual" /> is returned.
/// </summary>
public static TResult IfEqualReturn<TValue, TResult>(this HtmlHelper html, TValue left, TValue right, TResult returnIfEqual, TResult returnIfNotEqual)
{
return EqualityComparer<TValue>.Default.Equals(left, right) ? returnIfEqual : returnIfNotEqual;
}
Notes:
- Use generics instead of
object to avoid boxing.
- Use
EqualityComparer<TValue> to check for equality. This class is very efficient, avoids boxing, and does a good job of handling the primitive types correctly, uses IEquatable<T> if TValue implements it, and correctly evaluates reference equality versus value equality depending on TValue. It also will not throw an exception if left or right is null.
When you create any function (but extensions methods in particular), choosing a descriptive but succinct name is critical. Ideally, the name should be enough information for another developer to know what the function does without looking at its code.
- I chose
IfEqualReturn because, to me, the most important thing to understand about the function is that it evaluates the equality of left and right to determine what to return-- remember, any boolean value can be used for a ternary expression, so GetValueTernary leaves out the critical detail that this function specifically evaluates equality.
- Using XML comments is particularly important for extension methods. When you write your
<summary>, imagine that another developer is reading your code, and explain what he would need to know to understand what the call will do. Keep it brief-- it should fit easily in a tooltip. If you feel like you need to explain more, add a <remarks> element.
Here are some other suggestions.
The .NET Framework interface IEqualityComparer<T> allows you to create classes that evaluate equality of a given type T. The following function allows someone to pass in an instance, and falls back on EqualityComparer<T>.Default if one is not specified.
public static TResult IfEqualReturn<TValue, TResult>(this HtmlHelper html, TValue left, TValue right, TResult resultIfEqual, TResult resultIfNotEqual, IEqualityComparer<TValue> equalityComparer = null)
{
if (equalityComparer == null)
equalityComparer = EqualityComparer<TValue>.Default;
return equalityComparer.Equals(left, right) ? resultIfEqual : resultIfNotEqual;
}
One place where this comes in handy is when comparing strings (see StringComparer). Usage:
var r1 = Html.IfEqualReturn("str1", "str2", true, false, StringComparer.Invariant); // r1 = false
var r2 = Html.IfEqualReturn("str1", "str1", true, false, StringComparer.Invariant); // r2 = true
var r3 = Html.IfEqualReturn("str1", "STR1", true, false, StringComparer.Invariant); // r3 = false
var r4 = Html.IfEqualReturn("str1", "STR1", true, false, StringComparer.InvariantIgnoreCase); // r4 = true
... or you could create one that uses a lambda expression:
public static TResult IfTrueThen<TValue, TResult>(this HtmlHelper html, TValue left, TValue right, TResult returnIfTrue, TResult returnIfFalse, Func<TValue, TValue, bool> evaluateFunc)
{
return evaluateFunc(left, right) ? returnIfTrue : returnIfFalse;
}
// Usage:
var r1 = Html.IfTrueThen(0, 1, true, false, (l, r) => l == r); // r1 = false
var r2 = Html.IfTrueThen("string", "STRING", true, false, (l, r) => String.Equals(l, r, StringComparison.InvariantIgnoreCase)); // r2 = true
Another way:
public static TResult IfTrueThen<TResult>(this HtmlHelper html, Func<HtmlHelper, bool> evaluateFunc, TResult resultIfTrue, TResult resultIfFalse)
{
return evaluateFunc(html) ? resultIfTrue : resultIfFalse;
}
// Usage:
int v1 = 0, v2 = 0;
var r1 = Html.IfTrueThen(h => v1 == v2, true, false); // r1 = true
v1 = 4;
var r2 = Html.IfTrueThen(h => v1 == v2, true, false); // r2 = false
var r3 = Html.IfTrueThen(h => (v1 - 4) == v2, true, false); // r3 = true
or...
<div class="@Html.IfTrueThen(h => Model.UserVoteTypeId == VoteType.UpVote, "us", "u")">...</div>
return (a.Equals(b) ? valueIfEqual : valueIfNotEqual).ToString()\$\endgroup\$<div class="@(Model.UserVoteTypeId == VoteType.UpVote ? "us" : "u")">...</div>? \$\endgroup\$