Oop 如何在Bool或Iff中实现Exp,从面向大众的纸张扩展性出发
我目前正在研究面向大众的纸张扩展性。Bruno C.d.提出的对象代数的实用可扩展性。S.Oliveira和William R.Cook(可在互联网上的许多地方找到,例如:) 在第10页,他们写道: 添加新的数据变量很容易。第一步是创建新类Oop 如何在Bool或Iff中实现Exp,从面向大众的纸张扩展性出发,oop,computer-science,extensibility,Oop,Computer Science,Extensibility,我目前正在研究面向大众的纸张扩展性。Bruno C.d.提出的对象代数的实用可扩展性。S.Oliveira和William R.Cook(可在互联网上的许多地方找到,例如:) 在第10页,他们写道: 添加新的数据变量很容易。第一步是创建新类Bool 和Iff通常的面向对象风格(如Lit和Add): Exp的实现似乎留给读者作为练习。然而,我不清楚Exp在本文的这一部分是如何定义的。我的问题是: 应如何实施Bool和Iff 以下是我尝试过的: Exp 在本文的早期,Exp接口的定义如下: inte
Bool
和Iff
通常的面向对象风格(如Lit
和Add
):
Exp
的实现似乎留给读者作为练习。然而,我不清楚Exp
在本文的这一部分是如何定义的。我的问题是:
应如何实施Bool
和Iff
以下是我尝试过的:
Exp
在本文的早期,Exp
接口的定义如下:
interface Exp {
Value eval();
}
此处,值
由另一个接口定义:
interface Value {
Integer getInt();
Boolean getBool();
}
interface IntAlg<A> {
A lit(int x);
A add(A e1, A e2);
}
interface Exp {
int eval();
}
然而,这篇论文很快就偏离了Exp
的定义,转而采用基于访客的定义
Bool的可能实现
基于这个定义,应该如何实现Bool
类
像这样的事情似乎是一个开始:
class Bool implements Exp {
boolean x;
public Bool(boolean x) { this.x = x; }
public Value eval() {
return new VBool(x);
}}
然而,问题是如何正确地实现值
该文件仅表明:
class VBool implements Value {...}
在我看来,实施并不全面:
class VBool implements Value {
boolean x;
public VBool(boolean x) { this.x = x; }
public Boolean getBool() {
return new Boolean(x);
}
public Integer getInt() {
// What to return here?
}
}
正如我上面的尝试所示,不清楚从getInt
返回什么。我想我可以返回null或抛出异常,但这意味着我的实现是空的
在任何情况下,Exp
的第一个定义似乎只是本文中的一个激励性示例,然后继续定义一个更好的替代方案
Exp
在第4页,论文将Exp
重新定义为内部访问者:
interface Exp {
<A> A accept(IntAlg<A> vis);
}
没有办法凭空变出A
值,因此必须与vis
交互才能产生A
值。然而,vis
参数仅定义lit
和add
方法
lit
方法需要int
,这在Bool
中不可用
同样,add
需要两个A
值,这两个值也不可用。我再次发现自己陷入僵局
Exp
的第三个定义?
然后,在第8页,本文展示了这个例子:
int x = exp(base).eval();
这里,exp(base)
返回exp
,但这是eval
的哪个定义
显然,Exp
仍然(或者再次?)有一个eval
方法,但现在它返回int
。它看起来像这样吗
interface Exp {
int eval();
}
这篇论文没有给出这个定义,所以我可能误解了什么
Bool的可能实现
我们能用这个Exp
的定义来实现Bool
和Iff
吗
class Bool implements Exp {
boolean x;
public Bool(boolean x) { this.x = x; }
public <A> A accept(IntAlg<A> vis) {
// What to return here?
}}
class Bool implements Exp {
boolean x;
public Bool(boolean x) { this.x = x; }
public int eval() {
// What to return here?
}}
同样,不清楚如何实现该接口。当然,可以返回0
表示false,返回1
表示true,但这只是一个任意的决定。这似乎不合适
有没有第四个我没有的Exp
定义?或者报纸上还有什么其他信息让我摸不着头脑
顺便说一句,如果我在尝试中犯了错误,我道歉。我通常不写Java代码。@Mark。让我试着澄清一下你的困惑点
Exp的定义
我们在第10页中总结的Exp定义为:
interface Exp {
Value eval();
}
这在前面的文章中如图1所示。可以忽略带有访问者的Exp的替代版本。我们只是用它来讨论访问者以及与对象代数的关系,它在本文后面的部分中不起作用
另外,关于第8页的代码,我认为这篇文章有一个拼写错误。你是对的:似乎我们假设了一个eval方法,它返回int
。当我们写这篇论文时,我们使用了Exp的多个版本,可能是我们错误地使用了另一个版本的代码。第8页中的代码适用于论文中的表述,应为:
int x = exp(base).eval().getInt();
价值的选择
我们打算用于实现Value类的代码使用异常,类似于您自己的尝试,正如本文所述,它确实是部分的。在本文中,我们的观点是关于源表达式的可扩展性和类型安全性。对于这些值,我们想要的只是值足够丰富,可以支持源表达式,并且假设值本身不可扩展(稍后在第7节中,我们将简要讨论可扩展值)。我们在本文中选择的表示法旨在保持代码的简单性,并避免在处理错误管理(与可扩展性正交)时出现一些干扰
令人满意的是,这不是一个很好的表示,但至少在当时的Java版本中,它似乎是一个合理的折衷方案。在现代Java中,我认为应该将值建模为代数数据类型。Java16支持,可用于在函数式编程中对代数数据类型进行基本建模。因此,您可以使用以下内容对价值进行建模:
sealed interface Value {}
record VInt(int x) implements Value {}
record VBool(boolean b) implements Value {}
回想起来,为了避免像你现在这样的困惑,我认为最好是简单地使用界面来展示论文:
interface Value {
Integer getInt();
Boolean getBool();
}
interface IntAlg<A> {
A lit(int x);
A add(A e1, A e2);
}
interface Exp {
int eval();
}
使用一个if
构造a la C,其中整数扮演布尔函数的角色。这本来可以避免因价值的表现而分心
论文中的价值表示
在任何情况下,回到论文的表述,以及你关于偏好的观点,我展示了一个最小但复杂的
// Values
interface Value {
Optional<Integer> intValue();
Optional<Boolean> boolValue();
}
// The expression interface
interface Exp {
Optional<Value> eval();
}