如何使我的通用比较器 (IComparer) 处理空值?

发布于 2024-10-15 06:21:12 字数 706 浏览 3 评论 0原文

我正在尝试编写一个用于排序的通用对象比较器,但我注意到它不能处理它所比较的​​值之一为空的实例。当一个对象为空时,我希望它像空字符串一样对待它。我尝试将 null 值设置为 String.Empty 但在调用 CompareTo() 时出现“对象必须是 String 类型”错误。

public int Compare(T x, T y)
{
    PropertyInfo propertyInfo = typeof(T).GetProperty(sortExpression);
    IComparable obj1 = (IComparable)propertyInfo.GetValue(x, null);
    IComparable obj2 = (IComparable)propertyInfo.GetValue(y, null);

    if (obj1 == null) obj1 = String.Empty; // This doesn't work!
    if (obj2 == null) obj2 = String.Empty; // This doesn't work!

    if (SortDirection == SortDirection.Ascending)
        return obj1.CompareTo(obj2);
    else
        return obj2.CompareTo(obj1);
}

我现在很纠结这个!任何帮助将不胜感激。

I'm trying to write a generic object comparer for sorting, but I have noticed it does not handle the instance where one of the values it's comparing is null. When an object is null, I want it to treat it the same as the empty string. I've tried setting the null values to String.Empty but then I get an error of "Object must be of type String" when calling CompareTo() on it.

public int Compare(T x, T y)
{
    PropertyInfo propertyInfo = typeof(T).GetProperty(sortExpression);
    IComparable obj1 = (IComparable)propertyInfo.GetValue(x, null);
    IComparable obj2 = (IComparable)propertyInfo.GetValue(y, null);

    if (obj1 == null) obj1 = String.Empty; // This doesn't work!
    if (obj2 == null) obj2 = String.Empty; // This doesn't work!

    if (SortDirection == SortDirection.Ascending)
        return obj1.CompareTo(obj2);
    else
        return obj2.CompareTo(obj1);
}

I'm pretty stuck with this now! Any help would be appreciated.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

一身骄傲 2024-10-22 06:21:12

除非您的 T 被有效地限制为字符串,否则您不能将您的 T 视为空字符串。您应该做的是制定一个比较空值的计划。例如

if (obj1 == null && obj2 == null)
   return 0;
else if (obj1 == null)
   return -1;
else if (obj2 == null)
   return 1;
else 
   return obj1.CompareTo(obj2);

You cannot treat your T as an empty string unless your T was effectively constrained to being a string. What you should do is have a plan for comparing nulls. Such as

if (obj1 == null && obj2 == null)
   return 0;
else if (obj1 == null)
   return -1;
else if (obj2 == null)
   return 1;
else 
   return obj1.CompareTo(obj2);
夜司空 2024-10-22 06:21:12
if (SortDirection == SortDirection.Ascending)
    return Comparer<T>.Default.Compare(obj1, obj2);
else
    return Comparer<T>.Default.Compare(obj2, obj1);
if (SortDirection == SortDirection.Ascending)
    return Comparer<T>.Default.Compare(obj1, obj2);
else
    return Comparer<T>.Default.Compare(obj2, obj1);
冬天旳寂寞 2024-10-22 06:21:12

由于 T 是泛型类型,因此您不能为其分配 String 值;您只能为其分配 T 类型的值。如果您只想用它来比较字符串,请使用 String 而不是 T。否则,添加 null 检查并决定 null 应该落在哪里。

Since T is a generic type, you cannot assign it a String value; you can only assign it a value of type T. If you are only going to use this to compare strings, use String instead of T. Otherwise, add null checking and decide where in order null should fall.

阿楠 2024-10-22 06:21:12
IComparable obj1 = (IComparable)propertyInfo.GetValue(x, null) ?? "";
IComparable obj2 = (IComparable)propertyInfo.GetValue(y, null) ?? "";

这基本上意味着 obj1 现在将是 propertyInfo.GetValue(x, null) 的值,或者,如果恰好为 null,则 obj1 将是“”。

或者,如果问题是 GetValue 在 null 上崩溃,您可以执行以下操作:

IComparable obj1 = "";
try { obj1 = (IComparable)propertyInfo.GetValue(x, null); } catch {}
IComparable obj1 = (IComparable)propertyInfo.GetValue(x, null) ?? "";
IComparable obj2 = (IComparable)propertyInfo.GetValue(y, null) ?? "";

This basically means that obj1 will now be the value of propertyInfo.GetValue(x, null) or, if that happens to be null, obj1 will be "".

Or if the problem is that the GetValue crashes on null you could do something like:

IComparable obj1 = "";
try { obj1 = (IComparable)propertyInfo.GetValue(x, null); } catch {}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文