2010-07-30 98 views
5

有很多人反对使用“public/private”静态方法。我有四处搜寻,没有运气,并试图找到任何提倡善用静态方法的人。什么时候应该使用公共静态方法

假设方法将永远是Cohesive哪里可以使用公共静态方法的可接受区域?这些方法在Java和.NET之间有所不同吗(又是另一种可以接受)?

这最近SO后刺激了我对这个话题的愤怒/兴趣。

+0

当您发布此问题时,您寻找的答案是什么? – Fenton 2010-08-04 08:00:02

+0

就像Michael Borgwardt的回答,我只是在等待看看有没有人对Java和.NET有什么不同。 – Nix 2010-08-04 12:29:20

回答

4

静态方法通常不应

  • 访问其参数之外的任何状态(因为其导致难以改变耦合)
  • 修改其参数(因为如果这样做,为什么它不是该参数的实例方法?)

相反,纯函数(即没有副作用)使良好的静态方法。

当然,这不应该被视为绝对的教条。

+0

Singleton GetInstance是修改静态状态的静态方法的最佳示例(可以启动单例对象) – Nix 2010-07-30 14:56:07

+0

@Nix:单例通常被认为不是一件好事。并且在访问器中初始化它们主要用于产生关于双重检查锁定的无穷无尽的讨论。 – 2010-07-30 15:47:29

5

如果该方法可以被视为一个单元,并且可以自行进行有效测试,则使用公共静态方法。在使用静态方法的类型上实现依赖注入或模仿很简单。

我使用的静态方法的效用方法很少/没有依赖关系,并定义良好的输入/输出。

+1

为什么在使用静态方法的类型上使用DI很困难?同意,如果你正在谈论嘲笑有静态方法的类... – Nix 2010-07-30 13:40:45

+0

@Nix:原谅我离开一点语言不可知论。在.NET中,静态方法不能是接口的成员。这减少了模拟对象时可用的选项,因为.NET仅支持类的单一继承,并且接口不描述整个类合同。请注意,在静态方法中使用DI *仍然是一回事,使用DI *和*静态方法很难。 – kbrimington 2010-07-30 13:52:14

2

我会说在简单工厂中使用它们是公平的,就像返回包含静态方法的类型的场景一样。这是不是一个巨大的飞跃,说如果:

string.Empty; 

是一个合法的静态财产则:

string.GenerateRandomString(); 

是一个合法的静态方法。但即使如此,我仍然可以看到纯粹的OO程序员可能更喜欢StringFactory或RandomStringGenerator类,但我想这一切都取决于您绘制线的位置。

+0

我把问题放在设计上,我的恐惧很明显的说不要使用静态方法!将不必要地增加代码复杂性。 在我们的领域里,它的全部关于理解何时需要“StringFactory”或“RandomStringGenerator”。 – Nix 2010-07-30 13:35:47

+0

@Nix:我同意。静态方法有它们的位置。在我的应用程序中,它们倾向于用于实用程序类。 – kbrimington 2010-07-30 13:55:31

0

将方法标记为静态会告诉消费者,您不会更改传入该方法的任何对象的状态。静态方法应该对其传递的参数执行操作,不应该依赖任何内部字段。

我相信在你引用的文章中给出的具体建议是关于静态方法的位置 - 而不是使用静态方法的建议。

+0

在我看来,这篇文章指的是不使用静态方法......因为静态方法缺乏内聚力,所以他们的方法。一个静态类只能*依赖内部静态字段*并且修改它们没有错误...?为什么静态方法不能改变传递给它们的对象? (假设其有目的) – Nix 2010-07-30 13:44:32

0

一个典型的用途是实现单例模式。

+0

没错,但我们中有些人认为辛格尔顿很少适合。请参见http://www.c2.com/cgi/wiki?SingletonsAreEvil – TrueWill 2010-07-30 14:41:07

+0

与其他工具一样,正确使用时,Singleton很好。这是导致问题的'正确使用'部分,人们很少正确使用它。 – 2010-07-30 14:47:32

0

我使用静态/共享的方法不是类的实例的一部分,或者如果我更新“共享”变量(记得使他们线程安全)。

通常,这意味着我最终将这些方法放在包含它们的不同“Manager”类中,我将构造函数标记为private,以确保它们不能实现。

附注:静态/共享方法是slightly faster,我记得在CLR中它们的实现与非OOP相关,并且不允许出现在与OOP语言中的设计缺陷有关的接口中。至少)Java固有的 - Discussed Here

0

静态方法与全局对象实例上的实例方法具有相同的语义。除非你对全局对象实例感兴趣,否则你不应该使用静态方法。这就是说,这取决于情况。有时候,讨厌的黑客是正确的做法。

相关问题