我正在编写一种编译语言是为了好玩,而且我最近因为使我的优化编译器非常健壮而受到鼓舞。我想出了几种优化某些东西的方法,例如,2 + 2 总是 4,所以我们可以在编译时进行数学运算, if(false){ ... } 可以完全删除等等,但是现在我已经开始循环了。经过一些研究,我认为我正在尝试做的并不是完全循环展开,但它仍然是一种优化技术。让我解释。
采取以下代码。
String s = "";
for(int i = 0; i < 5; i++){
s += "x";
}
output(s);
作为一个人,我可以坐在这里告诉你,这 100% 的时间相当于
output("xxxxx");
所以,换句话说,这个循环可以完全“编译”出来。这不是循环展开,而是我所说的“完全静态”,也就是说,没有输入会改变段的行为。我的想法是,任何完全静态的东西都可以解析为单个值,任何依赖输入或产生条件输出的东西当然不能进一步优化。那么,从机器的角度来看,我需要考虑什么?是什么让循环“完全静态”?
我想出了三种类型的循环,我需要弄清楚如何分类。每次运行后总是以相同的机器状态结束的循环,无论输入如何,循环永远不会完成,以及我无法找出一种或另一种方式的循环。如果我无法弄清楚(它会根据动态输入有条件地改变它将运行的次数),我并不担心优化。除非程序员特别禁止,否则无限循环将是编译错误/警告,并且每次都相同的循环应该直接跳过以使机器处于正确状态,而不循环。
当然要优化的主要情况是静态循环迭代,此时内部的所有函数调用也是静态的。确定循环是否具有动态组件很容易,如果它不是动态的,我想它必须是静态的。我无法弄清楚的是如何检测它是否会是无限的。有人对此有任何想法吗?我知道这是停机问题的一个子集,但我觉得它是可以解决的;停止问题是一个问题,因为对于某些程序子集,您无法判断它可能会永远运行,也可能不会,但我不想考虑这些情况,我只想考虑这些情况它会在哪里停止,或者它不会停止,但首先我必须区分这三种状态。