Smalltalk如何处理程序错误?

Smalltalk如何处理程序错误?,smalltalk,error-handling,Smalltalk,Error Handling,我是Smalltalk的新手。我读过一些关于它的文章和文件,我对它概念的完整性感到惊讶。它还提供了一些实时调试 无论如何,对于程序错误,错误意味着程序逻辑错误,程序累积的所有突变都是无效的。为了保证完整性,整个程序应该从某个点重新启动,并且整个程序状态应该是回滚 Smalltalk是如何处理的?(这个问题可能适用于所有动态REPL语言…Smalltalk使用异常对象。我建议你读一下这一章 它是Pharo By Example book的一部分: 关于变异、调试等,请注意Smalltalk将语言中

我是Smalltalk的新手。我读过一些关于它的文章和文件,我对它概念的完整性感到惊讶。它还提供了一些实时调试

无论如何,对于程序错误,错误意味着程序逻辑错误,程序累积的所有突变都是无效的。为了保证完整性,整个程序应该从某个点重新启动,并且整个程序状态应该是回滚


Smalltalk是如何处理的?(这个问题可能适用于所有动态REPL语言…

Smalltalk使用异常对象。我建议你读一下这一章

它是Pharo By Example book的一部分:

关于变异、调试等,请注意Smalltalk将语言中的很多东西具体化。例如,MethodContext类。这些对象表示VM正在执行的方法上下文。所以你可以检查它们,像玩一般的东西一样玩它们。编译方法也是如此。为了好玩,请检查“伪”变量“thisContext”:

如果您想自己回答问题,请查看调试器类。那么,您想知道在调试器中间重新启动方法时会发生什么吗?然后浏览方法#在Debugger中重新启动并遵循:)

实际上,您是在问“整个计算机如何回滚到已知状态?”因为Smalltalk映像是虚拟机,其意义与VMWare和VirtualBox相同


我们最接近于撤销任意副作用的能力(不包括像回滚I/O这样明显的不可能)可能是Alessandro Warth的世界,正如他在博士论文中所描述的那样。至少在一般意义上是这样的:当然可以使用Memento和Command模式来实现可撤销的操作。

我猜您指的是图像中的许多对象,它们在开发和调试时可能会进入不一致的状态。通常的过程是将代码存储在包中,如(Monticello代表squeak/pharo)。当您想要重置东西时,您将从发行版中获得一个干净的映像,并从包中重新加载代码。对于已部署的应用程序,除了软件包中的代码外,通常还需要一些信息来重新创建以某种外部形式存储的数据对象,如文件中存储的序列化形式,或dql或noSql数据库中存储的数据对象。因此,您的重置过程将是获取新图像,从包中加载代码,从外部存储加载数据模型对象。

事实并非如此

从smalltalks中我知道他们都不支持这种交易。设置执行期间累积的所有副作用。不支持自动回滚。有研究正在进行如何支持这一点,但没有尝试AFAIK。您必须知道,如果您正在调试,并且在堆栈跟踪中返回,则对象没有处于执行时的状态。您只看到处于最新状态的对象

虽然以一种通用的方式支持这一点并不容易,但通过程序的设计可以解决这一问题。最突出的方法是:

  • 复制/克隆要修改的对象,并将更改应用于副本。如果出了问题,你就扔掉复印件。如果一切正常,您可以将副本的内容应用于原件。您可以使用memento模式解决此问题
  • 您将更改应用于对象,但如果出现问题,您将重新应用原始内容。这可以通过使用命令模式执行do/undo操作来实现