Łukasiewicz谓词逻辑?

时间:2015-11-29 11:04:37

标签: java java-8 predicate

有没有办法用Java API模拟Łukasiewicz的三值逻辑?

更具体地说,我想效仿Łukasiewicz''M' ("it is not false that...")运营商。

例如,我需要构造这个Predicate<String>,它会得到以下结果:

predicate.test("0") = false
predicate.test(null) = true
predicate.test("1") = true

当否定时,给出:

predicate.negate().test("0") = true
predicate.negate().test(null) = true
predicate.negate().test("1") = false

如果要测试的值为A,我的谓词会计算MAnegate()所做的是计算¬MA,而我希望它计算M¬A

P.S。不要用Predicate的三值替换boolean替换pst1.setString(1,cl1.toUpperCase()); // here pst1 is null in your posted code. 的三值替换来解决问题,因为我非常清楚自己如何做到这一点。我问这个问题是为了找出纯Java8是否可行,只需要很少的额外编码工作。

2 个答案:

答案 0 :(得分:2)

看起来这就是你想要的:

static <T> Predicate<T> p(Predicate<? super T> o){ //(I'm not sure what to name this)
    return new Predicate<T>(){
        @Override
        public boolean test(T t) {
            return t == null || o.test(t);
        }
        @Override
        public Predicate<T> negate(){
            return p(o.negate());
        }
    };
}
....
Predicate<String> predicate = p(t -> !"0".equals(t));

如果要测试的值为null,则返回true,否则我们使用原始谓词。否定我们只是否定原始谓词。

如果null并不总是第三个值,你可以传入另一个谓词来测试它:

static <T> Predicate<T> p(Predicate<? super T> isUnknown, Predicate<? super T> isTrue){
    return new Predicate<T>(){
        @Override
        public boolean test(T t) {
            return isUnknown.test(t) || isTrue.test(t);
        }
        @Override
        public Predicate<T> negate(){
            return p(isUnknown, isTrue.negate());
        }
    };
}

答案 1 :(得分:1)

如果我们在Predicate类中保留negate()的默认实现,则不可能这样做:默认情况下,这构造一个始终返回初始的相反布尔值的谓词谓语。因此,predicate.test(null)predicate.negate().test(null)都不可能返回true

因此,我们需要实现自己的谓词。在以下实现中,使用negate布尔值维护状态。它表示要为trueValuefalseValue返回的正确值。对于thirdValue,始终返回true。如果使用既不是3个值之一的值测试谓词,则始终返回false(此问题在您的问题中未提及,因此请随意对其进行调整)。

public static void main(String... args) {
    Predicate<String> predicate = lukasiewicz("1", "0", null);

    System.out.println(predicate.test("0"));
    System.out.println(predicate.test(null));
    System.out.println(predicate.test("1"));

    System.out.println(predicate.negate().test("0"));
    System.out.println(predicate.negate().test(null));
    System.out.println(predicate.negate().test("1"));
}

private static <T> Predicate<T> lukasiewicz(T trueValue, T falseValue, T thirdValue) {
    class LukasiewiczPredicate implements Predicate<T> {

        private boolean negate; 

        private LukasiewiczPredicate(boolean negate) {
            this.negate = negate;
        }

        @Override
        public boolean test(T t) {
            if (Objects.equals(trueValue, t)) return negate;
            if (Objects.equals(falseValue, t)) return !negate;
            if (Objects.equals(thirdValue, t)) return true;
            return false;
        }

        @Override
        public Predicate<T> negate() {
            return new LukasiewiczPredicate(!negate);
        }

    };
    return new LukasiewiczPredicate(true);
}