可能重复:
C#中的安全导航操作员?
"如果object为null,则为null;如果object为null,则为object.member"的快捷方式
在我的XML处理项目中,我必须浏览链式属性以获得所需的值.例如,obj1.obj2.obj3.obj4.obj....Value.并且可能退出此链中的任何对象为null.
我用Google搜索了"c#中的NullSafe导航"并找到了一些不错的文章.从Post之一,我有了实现自定义扩展的想法.现在我对这个扩展的性能有疑问.我有这3个解决方案.任何人都可以建议我采用哪一种(在性能方面)?
选项1(使用本文中解释的逻辑):
//custom extension method
public static TOutput IfNotNull<TInput, TOutput>(this TInput x, Func<TInput, TOutput> f)
where TInput : class
where TOutput : class
{
return x == null ? null : f(x);
}
//with custom extension method -- Very neat & clean.. but what about performance?
string x = obj1
.IfNotNull(x => x.obj2)
.IfNotNull(x => x.obj3)
.IfNotNull(x => x.obj4)
.IfNotNull(x => x.obj5)
.IfNotNull(x => x.Value);
Run Code Online (Sandbox Code Playgroud)选项2:
//with NullCheck -- probably right way?
if(obj1 != null
&& obj1.obj2 != null
&& obj1.obj2.obj3 != null
&& obj1.obj2.obj3.obj4 != null
&& obj1.obj2.obj3.obj4.obj5 != null)
{
string x = obj1.obj2.obj3.obnj4.obj5.Value;
}
Run Code Online (Sandbox Code Playgroud)2选项:
//with try-catch.. With lowest cyclomatic complexity, but not a right approach.
try
{
string x = obj1.obj2.obj3.obnj4.obj5.Value;
}
catch(NullReferenceException ne)
{
//ignore exception
}
Run Code Online (Sandbox Code Playgroud)我绝对不会选择 try-catch 选项。这不仅是一种代码味道(异常驱动开发),而且如果您担心性能,异常处理也不是正确的选择。
我不太明白第二个选项。您是否必须将其放在您想要访问 Value 属性的任何地方?或者是在扩展方法中。
选项一看起来最干净。
关于性能:我认为您不会发现选项 1 和 2 之间有很大差异,但您可以在一个小型控制台项目中尝试一下。只需运行第一个和第二个选项(例如 1000 次)并计算所需的时间。不是精确的科学,但通常足以衡量性能差异。
我猜你不会看到很大的区别。我认为您正在练习微优化。除非您要在一个确实很重要的系统上运行,否则请采用对您来说最优雅的解决方案。
| 归档时间: |
|
| 查看次数: |
864 次 |
| 最近记录: |