Rep & Rep Independence & Rep Invariant & Abstraction Function

前言:接续前面的博客,将有关表示(Rep)的几个概念进行对比分析

文章目录

    • 1.What is Rep&Rep Independence?
    • 2.Rep Invariant & Abstraction Function

1.What is Rep&Rep Independence?

其实刚学到这里的时候看到这几个相似的概念,笔者还是挺懵的,一度连表示(Rep)本身是什么都不是很清楚,于是仔细研究了一下,现在分享一下我的见解。
我们知道,在java中我们经常自己定义所需要的数据类型,称之为ADT,那么你有没有想过ADT是靠什么来划分的呢?是ADT的内部实现吗?比如我要定义一个bool类型的变量,可以用int中0和非0来代表布尔型的true与false,那你又同时可以用int中的奇数与偶数来分别表示,我们关心的是这个嘛?
当然不是,我们关心的是它的true与false,其实这是我们在ADT上定义的操作。因此ADT是以定义在其上的操作来进行衡量的,比如字符串类型可能有连接操作,取子串操作,转换大小写操作,等等,只要设计的ADT也提供了这样的操作,我们就可以把它也叫做字符串类型。
在这种情况下,表示(Rep)到底指什么?在我的理解中,表示就是这些操作的基础,这些操作都是在表示上所进行的。
这是什么意思呢,就像前面定义一个bool类型的变量,可以用int中0和非0来代表布尔型的true与false,我们就说这是一种表示,那你又同时可以用int中的奇数与偶数来分别实现,这是另一种表示。那我们就说这是两种不同的表示(Rep).没有这些表示,操作自然是无法进行的,而每个操作其实也是在对表示进行操作。
而一般来讲,表示通常可以指ADT中的成员变量(fields),因为ADT上的“操作”就是对这些成员变量进行操作的。
再举一个例子,我们可以自己来实现字符串String类型,这里称之为MyString,那么我们就需要完成String这个ADT需要的操作:
Rep & Rep Independence & Rep Invariant & Abstraction Function_第1张图片
针对这些同样的操作,我们却可以采用不同的表示,这里就体现为用不同的成员变量来实现操作:
第一种:字符数组

	private char[] a;

Rep & Rep Independence & Rep Invariant & Abstraction Function_第2张图片
第二种:字符数组+起点终点记录

	private char[] a;
	private int start;
	private int end;

Rep & Rep Independence & Rep Invariant & Abstraction Function_第3张图片
而这种可以在不影响外部功能(MyString的功能全部实现)的前提下可以采用不同的表示来完成操作的特性即为表示独立性(Rep Independence).这在ADT的设计中还是非常重要的,因为这样将程序的变化与外界实现了一定程度的隔离!

2.Rep Invariant & Abstraction Function

前面两种解释完了,你可能接着会问,那Rep Invariant又是什么?为什么和它们长得那么像0.0?
Yeah,这里又要介绍新概念了。
以上面的MyString为例,client是在看和用的是什么呢?
是我们的两种表示嘛?用户知道自己在用的是一个形如[a][b][c][d][e]的字符数组嘛?
当然不是,这也是为什么我们要用private将其保护起来的原因,我们是要将内部表示与client隔离的,client在看的和用的,只不过是我们利用表示来"模拟"的新的抽象的形式:形如"abcde"的字符串。
因此,其实程序中的所有值是可以分为两个部分的
一部分由我们的内部表示构成表示空间R,另一部分则是利用表示来"模拟"的抽象空间A。
而我们程序所在做的,就是在R和A之间建立一种映射,即利用内部的表示来为client呈现一种抽象的形式:
Rep & Rep Independence & Rep Invariant & Abstraction Function_第4张图片
而这个映射,就是AF(Abstraction Function).
显然,AF必须要求为满射,因为client要求的所有值我们必须都能够提供,否则说明我们的程序有问题。
但反之,AF并不一定为单射,比如用户需要的值是长度处于0至10的字符串,那么显然我们用字符数组表示的范围要远远超过它,只有其中满足长度条件的才会被映射上。
这也就引出了Rep Invariant(真是千呼万唤始出来):
它是表示空间所有表示值中会被AF映射到抽象空间中的表示值的集合,我们可以称其为"合法的表示值"的集合。很显然,它是所有表示值的一个子集,其象征着程序的所有表示值中会被利用到来模拟client的抽象值的表示值集合。不包括在其中的,对于我们的程序并没有什么帮助,我们也无需过多去考虑它们。

你可能感兴趣的:(软件构造,java)