【问题标题】:OOP: Passing an object vs. passing attributes into a methodOOP:将对象与将属性传递给方法
【发布时间】:2011-06-30 23:12:34
【问题描述】:

在简洁的设计方面,哪个更可取?

1) 将一个对象(比如你自己)传递给另一个类方法,该方法将直接操作所传递对象的属性。

A 类内部...

B.doStuff(this);

2) 改为传递对象的属性,并将返回值分配回属性,或通过引用传递。

A 类内部...

this.var1 = B.doStuff(this.var1);

第一种方法的缺点是模棱两可,它不明确 B 在 A 中改变了什么。 第二种方法的缺点是,除非属性通过引用/指针传递,否则需要返回一个数组,如果最终传递了很多属性,也会构成更长的函数调用。我猜正确的选择取决于具体情况,但在我做出决定之前,还有其他人可以提出的其他优点/缺点吗?

编辑:由于将有大量属性传递给第二个类(我将某些任务委托给它),我认为它保证使用第一种方法在这种情况下。我想出的另一个缺点是 B 类只能访问 A 类中的公共属性和方法,而第二种方法允许 B 类操作 A 类可能不希望向公众透露的私有属性。但是再一次,使用第二种方法更常见,当然在只访问少数变量的情况下更可取。

【问题讨论】:

    标签: oop variables attributes argument-passing


    【解决方案1】:

    您应该选择为函数提供最少信息量但对函数的工作而言足够优化的设计。这样可以确保处理过程中预期的副作用最少。

    我认为这个问题归结为是通过引用还是通过值传递值。

    大多数函数应该至少没有副作用,但如果你的函数意图是处理在参数中传递的数据,那么传递整个类引用会更好。

    例如,当您在 Forms 绘制事件(在 C# 中)中引用图形对象时,已知操作将在传递的对象引用上完成(但肯定取决于您的要求和实现)。

    如果您的函数可以在不需要传递整个类引用的情况下正常工作,那么您应该再次选择它。但是请记住,按值传递大量参数会占用更多资源,因为每次都要创建一个新副本,因此要分配新的内存,而在通过引用时,您只是传递一个引用,因此不会分配新的内存。

    如果您希望您的方法对传递的数据没有副作用,则可以使用第二种设计,而是对提供的数据起作用并创建一个包含结果的新对象,然后您将其分配给所需的属性。

    通常代码读者的看法是,如果在赋值运算符的右侧调用了某个函数,那么他知道数据已经完成了某些事情,但是正在返回一个新的数据,因此他通常不希望它对作为参数提供的数据进行操作。如果读者只看到一个没有任何赋值运算符的函数调用,那么他希望对作为参数提供的数据进行一些处理。

    【讨论】:

    • 感谢您的意见,我认为防止被更改的保护是一个好点。
    【解决方案2】:

    你完全正确。选择实际上取决于这里的情况。如果您使用像 Hibernate 这样的 ORM,父域类通常会编写类似这样的内容来配置与子域类的双向依赖关系:-

    public void addChild(Child child) {
        children.add(child);
        child.setParent(this);
    }
    

    对于大多数其他情况,最好使您的方法参数显式...换句话说,只将您需要的字段传递给方法以执行任务。它使类图更易于理解,并且您知道 API 究竟试图完成什么,因为您知道实际的输入和生成的输出。

    【讨论】:

    • 是的,这就是我的意思,我认为指定将要更改的内容很重要,主要问题是我传递了很多变量,所以我想创建是有意义的两个类之间的关联并以这种方式设置委托...
    【解决方案3】:

    我更喜欢第二种方法,那么B类就不会对A类有任何依赖。

    【讨论】:

      猜你喜欢
      • 2017-06-21
      • 1970-01-01
      • 2013-06-26
      • 2011-09-20
      • 2015-08-18
      • 1970-01-01
      • 2013-05-18
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多