如何确定不变量是什么?

发布于 2024-11-24 19:51:48 字数 125 浏览 2 评论 0原文

很简单,当设计一个新类时,我如何找出不变量应该是什么?不变量的定义是什么?我听说它与有效性有关,但这仍然含糊不清。是什么使给定实例有效或无效是有争议的。

我应该跟着我的“直觉”感觉走吗?是否有指导方针来找出不变量是什么?

Quite simply, when designing a new class, how do I figure out what the invariant should be? What defines the invariant? I've heard that it's tied into validity, but that's still ambiguous. What makes a given instance valid or invalid is debatable.

Should I just go with my "gut" feeling? Are there guidelines for figuring out what the invariant is?

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

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

发布评论

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

评论(1

冰雪梦之恋 2024-12-01 19:51:48

不变式始终可以表示为谓词,参数是类的部分或全部状态变量(字段)。一类可以有多个不变量。例如,假设您有一个包含 initialBalancelistOfTransactionscurrentBalanceAccount 类。此外,我们将交易保存在排序(按日期)列表中。对于此类,至少应维护两个不变量:

1)initialBalance + sum(交易金额)= currentBalance
2) 对于 listOfTransactions 中的每个元素,位置 i 处的交易的 timestamp 应始终小于位置处的交易的 timestamp j 如果 i j。

不变量取决于类正在做什么以及类的实现方式。

比方说,我们可以再添加一个状态变量:closeDate,并且会出现另一个不变量:在 closeDate 之后,任何交易都不能有日期。

或者,如果列表不是按日期排序,而是按交易金额排序,则 invatians 会发生变化。

另一个例子:
假设您有一个 mutable Ellipse 类,它定义了两个字段:r1r2,其中包含 的设置器>r1r2。此类没有任何不变式,因为 r1 和 r2 的任何值都可以表示明确定义的椭圆。

现在,假设您创建了新的 Circle 类来扩展可变的 Ellipse。圆只有一个半径,加上不变量为 (r1==r2)。为了保持不变性,你必须禁止有人设置 r1 或 r2,这样 r1!=r2 就会发生。

另一方面,如果 EllipseCircle不可变,则您不必关心对象生命周期中的不变量,因为仅在施工期间检查状况。

通过前面的例子,我想解释一下
1) 不变量的建立和维护方式很大程度上取决于类之间关系的设计选择。
2)班级正在做什么
3)类是如何实现的。

不可变类在维护其不变性方面往往不太复杂,因为它们是在构造时建立的,并且永远不会改变。 (不变性还有许多其他好处 - 不在答案的范围内)

Invariant can be always represented as predicate with arguments being some or all state variables (fields) of the class. One class can have more then one invariant. For example, suppose you have an Account class that has initialBalance, listOfTransactions, currentBalance. Also, we keep the transactions in a sorted (by date) list . for This class there are at least two invariants that should be maintained:

1) initialBalance + sum(transaction amounts) = currentBalance
2) for every element in the listOfTransactions, the timestamp of the transactions at position i should be always less then the timestamp of the transaction at position j if i < j.

Invariants depend on what the class is doing and also how the class is implemented.

Let say, we can add one more state variable: closedDate, and one more invariant will appear: no transaction can have date after the closeDate.

Or if the list is not sorted by date, but by transaction amount, then the invatians would change.

Another example:
Let's suppose that you have mutable Ellipse class defined with two fields, r1 and r2 which has setters for r1 and r2. This class doesn't have any invariant, as any values for r1 and r2 can represent well defined ellipse.

Now let's suppose that you create new Circle class that extends the mutable Ellipse. The circle has only one radius add the invariant would be (r1==r2). In order to maintain the invariant, you have to disallow somebody setting r1 or r2, such that r1!=r2 happens.

On the other hand if the Ellipse and Circle are immutable you don't have to care for the invariants during the life of the objects, as the condition would be checked only during construction.

With the previous examples, i wanted to explain that
1) the way the invariants are established and maintained depends very much on the choice of design of the relations between the classes.
2) What the class is doing
3) How the class is implemented.

Immutable classes tend to be less complex to maintain their invariant, as they are established at construction, and never change. (Immutability has many other benefits too - not in scope of the answer)

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