C#反模式
长话短说:我发现网络是不可或缺的资源。对于初学者和专业人士都是如此。我还没有为C#找到这样的东西。因此,我将以社区维基的形式打开这个问题,并邀请每个人分享他们在这方面的知识。由于我是C#的新手,我对此非常感兴趣,但不能从一些反模式开始:/ 以下是我认为对C语言特别适用的答案,而不是其他语言 我只是复制/粘贴了这些!考虑一下对这些评论的看法。C#反模式,c#,anti-patterns,C#,Anti Patterns,长话短说:我发现网络是不可或缺的资源。对于初学者和专业人士都是如此。我还没有为C#找到这样的东西。因此,我将以社区维基的形式打开这个问题,并邀请每个人分享他们在这方面的知识。由于我是C#的新手,我对此非常感兴趣,但不能从一些反模式开始:/ 以下是我认为对C语言特别适用的答案,而不是其他语言 我只是复制/粘贴了这些!考虑一下对这些评论的看法。 抛出错误的异常: if (FooLicenceKeyHolder == null) throw new NullReferenceExceptio
抛出错误的异常:
if (FooLicenceKeyHolder == null)
throw new NullReferenceException();
类中的公共变量(改为使用属性) 除非该类是一个简单的数据传输对象
或者,甚至更好
if (myBooleanVariable != false)
{
...
}
if (myBooleanVariable != false)
{
...
}
像这样的构造通常被C
和C++
开发人员使用,其中布尔值的概念只是一种约定(0==false,其他都是true);这在C#或其他具有真正布尔值的语言中是不必要的(或不可取的)
不使用
在适当情况下使用:
object variable;
variable.close(); //Old code, use IDisposable if available.
variable.Dispose(); //Same as close. Avoid if possible use the using() { } pattern.
variable = null; //1. in release optimised away. 2. C# is GC so this doesn't do what was intended anyway.
类中的公共变量(改为使用属性)
除非该类是一个简单的数据传输对象
有关讨论和澄清,请参见下面的评论
或者更一般的情况:
object foo = 100;
int bar = int.Parse(foo.ToString());
这算是一般性的吗
public static main(string [] args)
{
quit = false;
do
{
try
{
// application runs here ..
quit = true;
}catch { }
}while(quit == false);
}
我不知道如何解释它,但这就像有人捕捉到一个异常,然后一遍又一遍地重试代码,希望以后能正常工作。就像发生IOException一样,他们只是反复尝试,直到它起作用。大量使用复杂的“页面加载”方法,这些方法想做任何事情。GC.Collect()
收集,而不是信任垃圾收集器。侮辱了德米特定律:
object variable;
variable.close(); //Old code, use IDisposable if available.
variable.Dispose(); //Same as close. Avoid if possible use the using() { } pattern.
variable = null; //1. in release optimised away. 2. C# is GC so this doesn't do what was intended anyway.
a.PropertyA.PropertyC.PropertyB.PropertyE.PropertyA =
b.PropertyC.PropertyE.PropertyA;
错误地重新引发异常。要重新显示异常,请执行以下操作:
try
{
// do some stuff here
}
catch (Exception ex)
{
throw ex; // INCORRECT
throw; // CORRECT
throw new Exception("There was an error"); // INCORRECT
throw new Exception("There was an error", ex); // CORRECT
}
私有自动实现属性:
private Boolean MenuExtended { get; set; }
- 不知道何时以及如何在空检查中使用“as”,而在try/catch中使用cast
- catch块中的“抛出异常”与“抛出”
- 实例化大量字符串,而不是使用StringBuilder
我在我们的项目中发现了这个,差点把椅子弄坏
DateTime date = new DateTime(DateTime.Today.Year,
DateTime.Today.Month,
DateTime.Today.Day);
不必要的强制转换(请信任编译器):
正在引发NullReferenceException
:
if (FooLicenceKeyHolder == null)
throw new NullReferenceException();
我说话总是带着口音
C++程序员:
if (1 == variable) { }
在C#中,如果键入if(1=变量)
,这将给您一个编译器错误,允许您按照自己的意思编写代码,而不必担心会伤到自己。在Java和C#中,我对这一点看得太多了
如果它也有额外的积分
else{
somethingelse = false;
}
不明白布尔是一个真正的类型,而不仅仅是一个惯例
或者,甚至更好
if (myBooleanVariable != false)
{
...
}
if (myBooleanVariable != false)
{
...
}
像这样的构造通常被C
和C++
开发人员使用,其中布尔值的概念只是一种约定(0==false,其他都是true);这在C#或其他具有真正布尔值的语言中是不必要的(或不可取的)
更新:重新表述最后一段,以提高其清晰度。在每个方法的顶部声明和初始化所有局部变量太难看了
void Foo()
{
string message;
int i, j, x, y;
DateTime date;
// Code
}
我经常会被这种var滥用绊倒:
var ok = Bar();
或者更好:
var i = AnyThing();
以这种方式使用var毫无意义,也一无所获。这只会使代码更难理解。这是真的,我亲眼看到了
public object GetNull()
{
return null;
}
它实际上是在应用程序中使用的,甚至还附带了一个存储过程,一个将返回null的sp_GetNull
这让我很开心
我认为sp用于一个经典的asp站点。。与结果集有关的内容。net是一个将代码“转换”为.net的想法…使用属性进行任何操作,而不是简单地检索一个值或可能是一个便宜的计算。如果要从属性访问数据库,则应将其更改为方法调用。开发人员预计方法调用可能代价高昂,但他们不希望属性会这样 我经常看到以下代码:
if (i==3)
return true;
else
return false;
应该是:
return (i==3);
(请参见链接以获取解释和修复)我参与的项目有50个类,都继承自同一个类,它们都定义为:
要么把它放在父类中,要么把实用程序类放在一旁。啊
您是否考虑过浏览?以使用字符串连接而不是字符串生成器来关联任意数量的字符串
范例
foreach (string anItem in list)
message = message + anItem;
我看到转换成c#的人偶尔会这样做,不使用三元
你看,
private string foo = string.Empty;
if(someCondition)
foo = "fapfapfap";
else
foo = "squishsquishsquish";
而不是:
private string foo = someCondition ? "fapfapfap" : "squishsquishsquish";
在我继承的系统中发现过几次
if(condition){
some=code;
}
else
{
//do nothing
}
反之亦然
if(condition){
//do nothing
}
else
{
some=code;
}
”努夫说
if(data != null)
{
variable = data;
}
else
{
variable = new Data();
}
可以更好地写成
variable = (data != null) ? data : new Data();
variable = data ?? new Data();
写得更好的是
variable = (data != null) ? data : new Data();
variable = data ?? new Data();
最后一个代码清单在.NET2.0及更高版本中运行我实际上已经看到了这一点
bool isAvailable = CheckIfAvailable();
if (isAvailable.Equals(true))
{
//Do Something
}
轻松击败isAvailable==true
反模式
让这成为一个超级反模式 两个字符串反模式
反模式#1
检查字符串是否为null或空
//Bad
if( myString == null || myString == "" )
OR
if( myString == null || myString.Length == 0 )
//Good
string.IsNullOrEmpty(myString)
反模式#2(仅适用于.NET 4.0)
检查字符串是否为空或空白
//Bad
if( myString == null || myString == "" || myString.Trim() == "")
//Good
string.IsNullOrWhiteSpace(myString)
这什么?为什么?-总部-你不可能告诉我有人做了这件事?实际上我已经从我们的代码库中重构了很多_o@matthew:添加了一个更一般的情况(来自datatable的aka,呵呵)是的,好的,我可以看到人们为一个对象这样做。但是对于一个int
到int
的作业……我没有骗你,我见过有人这样做,这是我经历过的许多WTF时刻之一。@Spence:.Close()
不一定是“旧代码”。有些类提供了一个Close()
方法作为Dispose()
的别名,其中Close在语义上更有意义。True。但强制IDisposable允许您使用静态分析工具来发现实现ID的类型
variable = data ?? new Data();
bool isAvailable = CheckIfAvailable();
if (isAvailable.Equals(true))
{
//Do Something
}
//Bad
if( myString == null || myString == "" )
OR
if( myString == null || myString.Length == 0 )
//Good
string.IsNullOrEmpty(myString)
//Bad
if( myString == null || myString == "" || myString.Trim() == "")
//Good
string.IsNullOrWhiteSpace(myString)