自定义谓词链接

时间:2018-09-29 04:15:47

标签: java java-8

我正在学习Java 8。我正在尝试如下创建自定义谓词链接方法

@FunctionalInterface
public interface Predicate<T> {

    boolean test(T t);

    default Predicate<T> and(Predicate<T> other){
        return t -> this.test(t) && other.test(t);
    }
}

当我如上所述定义谓词时,它可以工作,但是如果我尝试实现与下面相同的谓词,则会给我StackOverflow异常

@FunctionalInterface
public interface Predicate<T> {

    boolean test(T t);

    default Predicate<T> and(Predicate<T> other){
        //return t -> this.test(t) && other.test(t);
        return new Predicate<T>() {
            @Override
            public boolean test(T t) {
                return test(t) && other.test(t);
            }
        };
    }
}

能否请您解释一下为什么它会给我Java 7风格的stackoverflow异常,而如果我使用lambda定义它则不给任何异常。

1 个答案:

答案 0 :(得分:6)

test(t)是对自身的递归调用,因为不合格的调用是对匿名类的调用。

this.test(t)也会这样,因为this是指匿名类。

更改为Predicate.this.test(t)

@FunctionalInterface
public interface Predicate<T> {

    boolean test(T t);

    default Predicate<T> and(Predicate<T> other){
        //return t -> this.test(t) && other.test(t);
        return new Predicate<T>() {
            @Override
            public boolean test(T t) {
                return Predicate.this.test(t) && other.test(t);
            }
        };
    }
}

有关更多详细信息,请参见answer to "Lambda this reference in java"