-
Notifications
You must be signed in to change notification settings - Fork 14
/
CalculatorProperties.java
60 lines (52 loc) · 1.66 KB
/
CalculatorProperties.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
package challenges.calculator;
import challenges.*;
import net.jqwik.api.*;
import net.jqwik.api.lifecycle.*;
import static net.jqwik.api.Tuple.*;
@Label("Calculator")
@AddLifecycleHook(ShrinkingStatistics.class)
public class CalculatorProperties {
@Label("calculator")
@Property
void test(@ForAll("expression") Object expression) {
Assume.that(divSubterms(expression));
evaluate(expression);
}
private boolean divSubterms(final Object expression) {
if (expression instanceof Integer) {
return true;
}
@SuppressWarnings("rawtypes")
Tuple3 tupleExpression = (Tuple3) expression;
if (tupleExpression.get1().equals("/") && tupleExpression.get3().equals(0)) {
return false;
}
return divSubterms(tupleExpression.get2()) && divSubterms(tupleExpression.get3());
}
@Provide
Arbitrary<Object> expression() {
return Arbitraries.lazyOf(
Arbitraries::integers,
Arbitraries::integers,
Arbitraries::integers,
() -> Combinators.combine(expression(), expression())
.as((e1, e2) -> of("+", e1, e2)),
() -> Combinators.combine(expression(), expression())
.as((e1, e2) -> of("/", e1, e2))
);
}
int evaluate(Object expression) {
if (expression instanceof Integer) {
return (int) expression;
}
@SuppressWarnings("rawtypes")
Tuple3 tupleExpression = (Tuple3) expression;
if (tupleExpression.get1().equals("+")) {
return evaluate(tupleExpression.get2()) + evaluate(tupleExpression.get3());
}
if (tupleExpression.get1().equals("/")) {
return evaluate(tupleExpression.get2()) / evaluate(tupleExpression.get3());
}
throw new IllegalArgumentException(String.format("%s is not a valid expression", expression));
}
}