【问题标题】:What are the downsides to static methods?静态方法的缺点是什么?
【发布时间】:2008-10-16 05:21:07
【问题描述】:

在网站业务层中使用静态方法与实例化一个类然后调用该类的方法相比有什么缺点?两种方式的性能表现如何?

【问题讨论】:

    标签: asp.net oop


    【解决方案1】:

    性能差异可以忽略不计。

    使用静态方法的缺点是它变得不太可测试。当依赖关系以静态方法调用表示时,您不能用模拟/存根替换这些依赖关系。如果所有依赖项都表示为接口,其中实现被传递到组件中,那么您可以使用组件的模拟/存根版本进行单元测试,然后将真正的实现(可能与 IoC 容器挂钩)用于真实的部署。

    【讨论】:

    • 视情况而定。 System.Math 静态类似乎并不比非静态类的可测试性差。我错了吗,乔恩?
    • 并不是静态方法本身不可测试 - 而是 using 静态方法的东西不可测试,因为您无法将静态方法的实现替换为一个简单的。例如,如果方法命中数据库,你的测试也会。
    【解决方案2】:

    Jon Skeet 是对的——性能差异将是微不足道的......

    话虽如此,如果您正在构建企业应用程序,我建议您使用 Microsoft 和许多其他软件公司所支持的传统分层方法。让我简单解释一下:

    我将使用 ASP.NET,因为我最熟悉它,但这应该很容易转化为您可能使用的任何其他技术。

    应用程序的表示层将由用于显示的 ASP.NET aspx 页面和用于“过程控制”的 ASP.NET 代码隐藏组成。这是谈论单击提交时发生的事情的一种奇特方式。我要转到另一个页面吗?有验证吗?我需要将信息保存到数据库吗?之后我该去哪里?

    流程控制是表示层和业务层之间的联络点。该层分为两部分(这就是您的问题所在)。构建这一层最灵活的方法是拥有一组业务逻辑类(例如 PaymentProcessing、CustomerManagement 等),其中包含 ProcessPayment、DeleteCustomer、CreateAccount 等方法。这些都是静态方法。

    当从流程控制层调用上述方法时,它们将处理业务对象的所有实例化(例如,客户、发票、付款等)并应用适当的业务规则。

    您的业务对象将处理与您的数据层的所有数据库交互。也就是说,他们知道如何保存他们包含的数据……这类似于 MVC 模式。

    那么——这样做有什么好处?好吧,您仍然可以获得多个级别的可测试性。您可以测试您的 UI,您可以测试业务流程(通过使用适当的数据调用业务逻辑类),您可以测试业务对象(通过手动实例化它们并测试它们的方法。您还知道,如果您的数据模型或对象发生更改,您的 UI 不会受到影响,只有您的业务逻辑类需要更改。此外,如果业务逻辑发生更改,您可以更改这些类而不影响对象。

    希望这会有所帮助。

    【讨论】:

      【解决方案3】:

      在性能方面,使用静态方法避免了对象创建/销毁的开销。这通常不重要。

      它们应该只用于方法采取的操作与状态无关的情况,例如工厂方法。创建一个对象实例只是为了实例化另一个对象实例是没有意义的:-)

      String.Format()、TryParse() 和 Parse() 方法都是静态方法有意义的好例子。它们总是执行相同的操作,不需要状态并且相当普遍,因此实例化没有多大意义。

      另一方面,在没有意义的情况下使用它们(例如,必须将所有状态传递给方法,例如,使用 10 个参数),会使一切变得更复杂、更难维护、更难读和更难测试正如乔恩所说。我认为这与业务层或代码中的其他任何地方无关,仅在情况合理时才使用它们。

      【讨论】:

      • "创建一个对象实例只是为了实例化另一个对象实例是没有意义的 :-)" - 如果您需要告诉某人如何在可模拟对象中创建某种类型的实例,它确实如此/可插拔方式。这就是工厂模式。
      【解决方案4】:

      如果该方法使用静态数据,这实际上将在您的 Web 应用程序的所有用户之间共享。

      纯代码,除了所有系统中静态方法的常见问题之外,没有真正的问题。

      【讨论】:

        【解决方案5】:
        1. 可测试性:静态依赖项的可测试性较低
        2. 线程:您可能会遇到并发问题
        3. 设计:静态变量就像全局变量

        【讨论】:

          猜你喜欢
          • 2011-01-29
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2020-12-27
          • 2011-05-06
          • 2010-10-30
          • 1970-01-01
          相关资源
          最近更新 更多