简体   繁体   English

我应该尽可能地让我的方法保持静态吗?

[英]Should I always make my methods static where possible?

I have often pondered this one... its probably an idiot question but here goes. 我经常思考这个问题......这可能是一个愚蠢的问题但是这里有。

Say I have this class: 说我有这个班:

public class SomeClass
{
    public int AProperty { get; set; }

    public void SomeMethod()
    {
        DoStuff(AProperty);
    }
}

Is there any advantage to doing this: 这样做有什么好处:

public class SomeClass
{
    public int AProperty { get; set; }

    public static void SomeMethod(int arg)
    {
        DoStuff(arg);
    }
}

The only advantage that is obvious is that I can now access SomeMethod directly. 唯一明显的优点是我现在可以直接访问SomeMethod

So is it good practice to make these kind of methods static where a little refactoring will allow or is it a waste of my time? 因此,如果一点点重构允许或浪费我的时间,将这些方法保持静态是一种好习惯吗?

EDIT: I forgot to mention (and ShellShock's comment reminded me) that the reason I ask is that I use ReSharper and it always makes suggestions that 'Method X can be made static' and so on... 编辑:我忘了提及(和ShellShock的评论提醒我),我问的原因是我使用ReSharper并且总是提出“方法X可以变为静态”的建议等等......

Static isn't evil. Static不是邪恶的。 Static is evil if used incorrectly, like many parts of our programming toolkit. 如果使用不正确, Static是邪恶的,就像编程工具包的许多部分一样。

Static can be very advantageous. Static可能非常有利。 As the accepted answer here points out, static can have a potential speed improvement. 正如这里接受的答案所指出的那样, static可以提高潜在的速度。

As a general rule if the method isn't using any fields of the class then its a good time to evaluate its function, however ultimately utility methods that can be called without instantiating an object can often be useful. 作为一般规则,如果该方法不使用该类的任何字段,那么它是评估其功能的好时机,但是最终可以在不实例化对象的情况下调用的实用方法通常是有用的。 For instance the DirectoryInformation and FileInformation classes contain useful static methods. 例如, DirectoryInformationFileInformation类包含有用的静态方法。

Edit 编辑

Feel obligated to point out that it does make mocking a lot harder but it is still definitely testable. 感觉有义务指出它确实让嘲弄变得更加困难但它仍然是可以测试的。

It just means you need to think harder about where static methods go, so that you can always test them without needing to rely on a mock/stub. 它只是意味着你需要想象的更难哪里 static方法去,让你随时可以测试他们,而不需要依赖于一个模拟/存根。 (ie: don't put them on your DTO that requires a persistent connection to the database). (即:不要将它们放在需要与数据库持久连接的DTO上)。

No. Static is evil . 不, 静电是邪恶的 It tightly couples the caller to the used class and makes it hard to test . 它将调用者与使用的类紧密耦合, 使其难以测试

Static methods make sense, if you should be able to call them without creating an object of the class before. 静态方法是有意义的,如果你应该能够在不创建类的对象之前调用它们。 In Java, for example, the Math-Class contains only static methods, because it wouldn't make much sense to instanciate a Math-Class only to do mathematical operations on other objects. 例如,在Java中,Math-Class只包含静态方法,因为仅仅为了对其他对象进行数学运算来实例化Math-Class没有多大意义。

Most of the time it's better to avoid static methods. 大多数情况下,最好避免使用静态方法。 You should get familiar with object oriented programming - there are lots of good resources out there, explaining all the concepts like static methods, etc. 你应该熟悉面向对象的编程 - 有很多好的资源,解释所有的概念,如静态方法等。

I'll attempt to answer your specific question involving the code sample you provided. 我将尝试回答您涉及您提供的代码示例的特定问题。

If SomeMethod is only useful in the class it is declared in, I would avoid the static conversion and leave it as an instance method. 如果SomeMethod只在声明它的类中有用,我会避免静态转换并将其保留为实例方法。

If SomeMethod is useful outside of the class it is in, then factor it out of the class. 如果SomeMethod在它所在的类之外是有用的,那么将它排除在类之外。 This may be as a static method in a static utility class somewhere. 这可能是某个静态实用程序类中的静态方法。 To make it testable, ensure that all its dependencies are passed in to it as arguments. 要使其可测试,请确保将其所有依赖项作为参数传递给它。 If it has loads of dependencies, you might want to review the design and figure out exactly what it's supposed to be doing - it might be better as an instance method in one of the classes you're passing in to it. 如果它有很多依赖项,你可能想要查看设计并确切地弄清楚它应该做什么 - 它可能更好地作为你传递给它的一个类中的实例方法。

Some people say that static is evil. 有人说静电是邪恶的。 This is generally because of the pitfalls that mutable static state provides, where variables hang around from the point a static constructor is called to the tear down of an app domain, changing in between. 这通常是因为可变静态提供的陷阱,其中变量从一个静态构造函数被调用到应用程序域的拆除,在两者之间发生变化。 Code reliant on that state can behave unpredictably and testing can become horrendous. 依赖于该状态的代码可能会出现不可预测的行为,并且测试可能会变得非常可怕。 However, there is absolutely nothing wrong with a static method which does not reference mutable static state. 但是,静态方法没有引用可变静态的问题。

For a (very simple) example where a static is evil, but can be converted to a non-evil version, imagine a function that calculates someone's age: 对于(非常简单)静态是邪恶的例子,但可以转换为非邪恶版本,想象一个计算某人年龄的函数:

static TimeSpan CalcAge(DateTime dob) { return DateTime.Now - dob; }

Is that testable? 那可以测试吗? The answer is no. 答案是不。 It relies on the massively volatile static state that is DateTime.Now . 它依赖于大规模易变的静态状态,即DateTime.Now You're not guaranteed the same output for the same input every time. 每次都不能保证相同输入的输出相同。 To make it more test friendly: 为了使它更适合测试:

static TimeSpan CalcAge(DateTime dob, DateTime now) { return now - dob; }

Now all the values the function relies on are passed in, and it's fully testable. 现在函数所依赖的所有值都被传入,并且它是完全可测试的。 The same input will get you the same output. 相同的输入将为您提供相同的输出。

I think it will depend on the way you want to use the methods. 我认为这取决于你想要使用这些方法的方式。 Using a static method is okay if it is used as a common method over a few instances of the class. 如果将静态方法用作类的几个实例的常用方法,则可以使用静态方法。

For the sake of an example, say you have a string class and two strings A and B. To compare A and B, you can either have a A.CompareTo(B) method or String.Compare(A, B) method. 为了举例,假设您有一个字符串类和两个字符串A和B.要比较A和B,您可以使用A.CompareTo(B)方法或String.Compare(A,B)方法。

Please correct me if I am wrong. 如果我错了,请纠正我。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM