currying时出现Groovy错误

给出错误代码ideone here,对不起,我还没有给出一个更小的例子.

因为它有点长,我会解释它.

Unfoldr类和展开函数基本上与unfoldr在Haskell中的作用一起创建列表.但在这种情况下,我创建了一个迭代器.

map函数再次与Haskell中的map非常相似.它被传递一个迭代器,用迭代器作为“状态”调用unfoldr,并创建一个新的迭代器,它给出了与旧迭代器相同的结果,但是应用了给定的函数.

splitlist将列表分成n个列表,即splitlist(2)([1,2,3,4])导致迭代器首先给出[1,2]然后[3,4].

currify采用一种功能,允许一个人部分应用它.例如,

f = currify { a,b -> a + b }

平均值f(2,3)= 5,f(2)(3)= 5,f(2)是一个加2的闭包.我得到了这个并回答了this question.

弄清楚一个参数闭包应该对它没有任何作用,并且就像它上面的识别函数一样.

最后,我已经覆盖了>>迭代器上的运算符,所以我基本上可以像管道一样使用它.

我的问题是为什么F行失败了,但是A-E线都成功了?

代码(很长)就在这里,就像我说的那样,也是在ideone.

@groovy.transform.TypeChecked

class Unfoldr<A,B> implements java.util.Iterator<A>
{
  public Unfoldr(Closure<Object[]> f,B init) 
  {
    this.f = f;
    this.state = f(init);
  }

  public synchronized A next() throws java.util.NoSuchElementException
  {
    if (hasNext())
    {
      A curr = state[0];
      state = f(state[1]);
      return curr;
    }
    else
    {
      throw new java.util.NoSuchElementException();
    }
  }

  public synchronized boolean hasNext() 
  {
    return state != null;
  }

  public void remove() { throw UnsupportedOperationException; }

  private Closure<Object[]> f;

  private Object[] state;
}

def currify(fn) {
    { Object... args ->
        if (args.size() == fn.maximumNumberOfParameters) {
            fn(*args)
        } else {
            currify(fn.curry(*args))
        }
    }
};

def unfoldr = currify { f,init -> new Unfoldr(f,init) };

def map = currify { f,l -> unfoldr({ l2 -> if (l2.hasNext()) { def e = l2.next(); return [f(e),l2]} else { return null; } },l.iterator())}

def splitlist = currify {
n,l ->
  unfoldr(
    { 
      l2 -> 
        try 
        { 
          def a = new Object[n];
          for (i in 0..(n-1))
          {
            a[i] = l2.next();
          }
          return [a,l2]; 
        } 
        catch (java.util.NoSuchElementException e) 
        {
          return null;
        }
    },l
  )
};

Iterator.MetaClass.rightShift = { PrintStream os -> delegate.each({ x -> os.println(x) }) }
Iterator.MetaClass.rightShift = { Closure f -> f(delegate) }

id = { x -> x }
f = currify { x -> x }

println "A: "
[[1,2],[3,4]].iterator() >> System.out
println "B: "
[1,4].iterator() >> splitlist(2) >> System.out
println "C: "
[[1,4]].iterator() >> map(id) >> System.out
println "D: "
[1,4].iterator() >> splitlist(2) >> map(id) >> System.out
println "E: "
[[1,4]].iterator() >> map(f) >> System.out
println "F: "
[1,4].iterator() >> splitlist(2) >> map(f) >> System.out

输出

A: 
[1,2]
[3,4]
B: 
[1,4]
C: 
[1,4]
D: 
[1,4]
E: 
[1,4]
F: 
Caught: java.lang.IllegalArgumentException: Can't curry 2 arguments for a closure with 1 parameters.
java.lang.IllegalArgumentException: Can't curry 2 arguments for a closure with 1 parameters.
    at prog$_currify_closure8.doCall(prog.groovy:42)
    at prog$_run_closure2_closure9.doCall(prog.groovy:49)
    at Unfoldr.<init>(prog.groovy:8)
    at prog$_run_closure1.doCall(prog.groovy:47)
    at prog$_currify_closure8.doCall(prog.groovy:40)
    at prog$_run_closure2.doCall(prog.groovy:49)
    at prog$_currify_closure8.doCall(prog.groovy:40)
    at prog$_run_closure5.doCall(prog.groovy:75)
    at prog.run(prog.groovy:91)

解决方法

看起来F行失败的原因

def e = l2.next()

返回Object []而不是ArrayList

相关文章

背景:    8月29日,凌晨4点左右,某服务告警,其中一个...
https://support.smartbear.comeadyapi/docs/soapui/steps/g...
有几个选项可用于执行自定义JMeter脚本并扩展基线JMeter功能...
Scala和Java为静态语言,Groovy为动态语言Scala:函数式编程,...
出处:https://www.jianshu.com/p/ce6f8a1f66f4一、一些内部...
在运行groovy的junit方法时,报了这个错误:java.lang.Excep...