如何封装只适用于少数方法的私有字段

发布于 2024-09-08 01:31:37 字数 1149 浏览 3 评论 0原文

我正在对类中的业务域对象进行建模,并且想知道正确封装仅适用于少数方法的私有字段的最佳方法是什么。

当我开始时,我的代码最初看起来像这样:

public class DiscountEngine
{
    public Cart As Cart { get; set;}
    public Discount As Discount { get; set;}

    public void ApplySKUGroupDiscountToCart()
    {
        ...
    }
}

但是,ApplySKUGroupDiscountToCart() 开始变得丑陋,因此我决定将代码重构为从 ApplySKUGroupDiscountToCart() 调用的更小的私有方法。我首先将大量局部变量传递到辅助方法中,但随后决定提取两个例程共有的变量,并将它们设为私有模块化变量。新代码如下所示:

public class DiscountEngine
{
    public Cart As Cart { get; set;}
    public Discount As Discount { get; set;}

    private int _SKUGroupItemDiscountsApplied = 0
    private int _SKUGroupTotalDiscounts = 0
    private int _SKUGroupID = 0

    public void ApplySKUGroupDiscountToCart()
    {
        ...
    }

    private void ApplyDiscountToSingleCartItem(ref CartItem cartI, 
                                               ref DiscountItem discountI)
    {
        ...
    }
}

一方面,三个私有整数字段可用于允许相关方法共享公共变量,而无需将它们作为参数来回传递。但是,这些变量仅适用于这些相关方法,我可能添加的任何其他方法都不需要看到它们。

有没有办法封装私有字段及其相关方法,同时仍保留为 DiscountEngine 类的一部分?有没有更好的方法来处理这个问题?

I'm working on modeling a business domain object in a class and am wondering what would be the best way to properly encapsulate private fields that only apply to a few methods.

When I started, my code originally looked like this:

public class DiscountEngine
{
    public Cart As Cart { get; set;}
    public Discount As Discount { get; set;}

    public void ApplySKUGroupDiscountToCart()
    {
        ...
    }
}

However, ApplySKUGroupDiscountToCart() was starting to get ugly, so I decided to refactor the code into smaller private methods that get called from ApplySKUGroupDiscountToCart(). I started by passing in lots of local variables into the helper method, but then decided to pull out variables common to both routines and make them private modular variables. The new code looks like this:

public class DiscountEngine
{
    public Cart As Cart { get; set;}
    public Discount As Discount { get; set;}

    private int _SKUGroupItemDiscountsApplied = 0
    private int _SKUGroupTotalDiscounts = 0
    private int _SKUGroupID = 0

    public void ApplySKUGroupDiscountToCart()
    {
        ...
    }

    private void ApplyDiscountToSingleCartItem(ref CartItem cartI, 
                                               ref DiscountItem discountI)
    {
        ...
    }
}

On the one hand, the three private integer fields are useful for allowing the related methods to share common variables without needing to pass them back and forth as parameters. However, these variables are only applicable to these related methods and any other methods I might add would have no need to see them.

Is there a way to encapsulate the private fields and their related methods while still remaining a part of the DiscountEngine class? Is there a better way altogether of dealing with this problem?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

梦途 2024-09-15 01:31:37

通常,将类字段设置为私有意味着“我有足够的纪律来确保该字段仅在该类中以适当的方式使用”。如果你的班级太大,你无法自信地说出这一点,那么也许班级正在尝试做太多不同的事情,应该分开(参见SRP)。

无论如何,理论已经足够了:-)。如果您想坚持使用一个类,那么您始终可以将这三个字段封装到一个私有嵌套类中,例如,

public class DiscountEngine
{
    public Cart As Cart { get; set;}
    public Discount As Discount { get; set;}

    private class SKUGroup
    {
        public int ItemDiscountsApplied = 0
        public int TotalDiscounts = 0
        public int ID = 0
    }

    public void ApplySKUGroupDiscountToCart()
    {
        ...
    }

    private void ApplyDiscountToSingleCartItem(ref CartItem cartI, 
                                               ref DiscountItem discountI)
    {
        ...
    }
}

这使您可以更自由地在代码中传递类的实例作为方法参数。

您可以更进一步,将任何作用于 SKU 数据的私有方法也移至嵌套类中。

Normally, making a class field private implies "I have enough discipline to ensure that this field is only used in an appropriate manner inside this class". If your class is too big for you to say that with confidence, then maybe the class is trying to do too many different things, and should be split up (see SRP).

Anyway, enough of the theory :-). If you want to stick with one class then you could always encapsulate those three fields into a private nested class, e.g.

public class DiscountEngine
{
    public Cart As Cart { get; set;}
    public Discount As Discount { get; set;}

    private class SKUGroup
    {
        public int ItemDiscountsApplied = 0
        public int TotalDiscounts = 0
        public int ID = 0
    }

    public void ApplySKUGroupDiscountToCart()
    {
        ...
    }

    private void ApplyDiscountToSingleCartItem(ref CartItem cartI, 
                                               ref DiscountItem discountI)
    {
        ...
    }
}

That gives you a bit more freedom to pass instances of the class around your code as method parameters.

You could take this a step further, and move any private methods that act on the SKU data into the nested class as well.

情丝乱 2024-09-15 01:31:37

首先,您很可能不需要将参数作为 ref 传递给 ApplyDiscountToSingleCartItem。简短版本:除非您实际上为您希望调用代码可见的变量分配一个值,否则您不需要ref。修改它们的变量和属性值对于调用代码来说是可见的,而无需将它们作为 ref 传递。

其次,无法在实例和本地之间确定变量的范围,这就是您所要求的。实现此目的的唯一方法是将此功能重构到另一个类中(可能是嵌套的私有类)。

但是,不要使用实例变量作为在函数之间传递数据的方式。如果数据在调用函数后变得“陈旧”,那么它应该是参数,而不是实例变量。

First things first, you very likely don't need to pass the parameters to ApplyDiscountToSingleCartItem as ref. Short version: unless you're actually assigning a value to the variable that you want to be visible to the calling code, you don't need ref. Modifying variable and property values on them will be visible to the calling code without passing them as ref.

Second, there is no way to scope a variable in between instance and local, which is what you're asking. The only way to accomplish this would be to refactor this functionality into another class (likely a nested private class).

Don't, however, use instance variables as a way to pass data between functions. If the data becomes "stale" after the function is called, then it should be a parameter, not an instance variable.

终陌 2024-09-15 01:31:37

我想说,我能想到的处理这个问题的唯一其他方法是将与它们关联的所有方法和私有变量提取到一个单独的类中。这样你就可以将所有内容封装起来。但不确定这在您的域对象的上下文中是否有意义。

I would say the only other way that I can think of to handle this would be to extract all the methods and private variables that are associated with them into a separate class. That way you keep all that encapsulated. But not sure if that would make sense in the context of your domain objects.

美人如玉 2024-09-15 01:31:37

您始终可以创建一个嵌套(内部)类来将具有共同用途的参数捆绑在一起。通过这种方式,您仍然可以将它们传递给您的私有方法,而不必传递 l.ots 参数 - 您只需传递私有类型的实例。

You could always create a nested (inner) class to bundle together parameters that have a common use. In this way you could still pass them to your private methods without having to pass around l.ots of arguments - you'd just pass an instance of the private type.

农村范ル 2024-09-15 01:31:37

“这些变量仅适用于这些相关方法,我可能添加的任何其他方法都不需要看到它们。”

首先,请记住,OO 开发的首要规则之一是构建客户想要的内容,然后应用 OO 设计,例如基本的 OO 规则和模式。你的引言几乎是在说你想为未知的事情做好计划。请注意,未知的是“更多相同”而不是新的需求。否则,这个类最终将成为一个God Object。

如果你发现你有很多方法不使用的成员,然后分而治之。

"these variables are only applicable to these related methods and any other methods I might add would have no need to see them."

First of all, keep in mind that one of the first rules of OO development is to build what the customer wants THEN apply OO design like basic OO rules and patterns. Your quote verges on saying you want to plan for the unknown. Be careful that the unknown is "more of the same" not NEW requirements. Otherwise, this class is going to end up becoming a God Object.

If you find you have many members that aren't used by the methods, then divide and conquer.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文