Unit testing 在groovy中使用memoize

Unit testing 在groovy中使用memoize,unit-testing,groovy,tdd,memoization,spock,Unit Testing,Groovy,Tdd,Memoization,Spock,我目前正在使用spock在groovy中实践测试驱动开发。 我有1组测试,其中3个不同的实现执行相同的操作:迭代、递归和记忆。 因此,我创建了一个抽象类来保存测试,然后创建了3个不同的文件来返回具体的类实现来运行测试。我有迭代和递归工作,但我在memoize()方面有问题 导入spock.lang.Specification 抽象类FibonacciTest扩展了规范{ 私人计算器 抽象def getCalculator() def设置(){ calculator=getCalculator()

我目前正在使用spock在groovy中实践测试驱动开发。 我有1组测试,其中3个不同的实现执行相同的操作:迭代、递归和记忆。 因此,我创建了一个抽象类来保存测试,然后创建了3个不同的文件来返回具体的类实现来运行测试。我有迭代和递归工作,但我在memoize()方面有问题

导入spock.lang.Specification
抽象类FibonacciTest扩展了规范{
私人计算器
抽象def getCalculator()
def设置(){
calculator=getCalculator()
}
def“测试金丝雀”(){
期望:
真的
}
//更多测试
}
类递归FibonacciTest扩展了FibonacciTest{
def getCalculator(){
新的递归计算器()
}
}
类迭代FibonacciTest扩展了FibonacciTest{
def getCalculator(){
新的迭代计算器()
}
}
类memorizefBonacciest扩展了FibonacciTest{
def getCalculator(){
新的MemoizeCalculator()
}
}
类递归计算器{
def getFibonacci(位置){
如果(位置<2){
1.
}
否则{
getFibonacci(位置-1)+getFibonacci(位置-2)
}
}
}
类迭代计算器{
def getFibonacci(位置){
如果(位置<2){
1.
}
否则{
def值=1
def previousValue=1
对于(我处于2..位置){
def临时值=以前的值
前一个值=前一个值
值=临时值+以前的值
}
价值
}
}
}
因此,我有迭代和递归的工作,但有问题,让备忘录工作。。我认为它应该和这个一起工作,但它不是。。有人知道我做错了什么吗

class MemoizeCalculator {
    def getFibonacci = { position ->
        if (position < 2)
            1
        else
            getFibonacci.call(position - 1) + getFibonacci.call(position - 2)
    }.memoize()
}
类记忆计算器{
def getFibonacci={位置->
如果(位置<2)
1.
其他的
getFibonacci.call(位置-1)+getFibonacci.call(位置-2)
}.memoize()
}

不能从声明变量的同一语句中引用该变量。要么将
getFibonacci.call
更改为
call
,要么在赋值之前声明变量(
def getFibonacci
)(
getFibonacci=…
)。

我尝试了def getFibonacci,然后将getFibonacci={position->…}.memoize()设置为所有文档所述的类型,但我总是遇到意外和其他错误。我想我就是不明白。。你能再明确一点吗?我不明白getFibonacci.call to call的变化。:/对不起,我只是在学编程。照我说的做就行了。将所有出现的
getFibonacci.call
替换为
call
(在闭包中,您不需要限定自己的方法),或者将
def getFibonacci={…}
替换为
def getFibonacci;getFibonacci={…}
。这两种解决方案对我都很有效。PS:如果遇到任何错误,请将其显示为问题的一部分(精确输出、堆栈跟踪等)。我选择尝试将
getFibonacci.call
替换为
call
,但出现以下错误。groovy.lang.MissingMethodException:没有方法签名:org.codehaus.groovy.runtime.memoize.memoize$MemoizeFunction.doCall()适用于参数类型:(java.lang.Integer)值:[0]可能的解决方案:call()、call([Ljava.lang.Object;)、call([Ljava.lang.Object;)、findAll()、equals(java.lang.Object)在FibonacciTest.test中,序列中的第一个数字是1(FibonacciTest.groovy:22),您如何调用该方法?
calculator.getFibonacci.call(5)
对我有效,但
calculator.getFibonacci(5)
给出了您显示的错误。不确定这是预期错误还是Groovy错误。我还发现,从Groovy 2.1.1开始,严格来说没有必要在闭包中省略
fibonacci。
根据我的记忆,在早期的Groovy版本中它是必需的。它被
calculator.getFibonacci(5)调用
,事实上,当我通过
calculator.getFibonacci.call(5)
调用该方法时,它会工作。但是,它会破坏我的迭代和递归测试。我可能会尝试您的其他选项
class MemoizeCalculator {
    def getFibonacci = { position ->
        if (position < 2)
            1
        else
            getFibonacci.call(position - 1) + getFibonacci.call(position - 2)
    }.memoize()
}