package aima.test.core.unit.logic.propositional.kb.data;
import java.util.HashSet;
import org.junit.Assert;
import org.junit.Test;
import aima.core.logic.propositional.kb.data.Clause;
import aima.core.logic.propositional.kb.data.Literal;
import aima.core.logic.propositional.parsing.ast.PropositionSymbol;
import aima.core.util.Util;
/**
*
* @author Ciaran O'Reilly
*
*/
public class ClauseTest {
private final Literal LITERAL_P = new Literal(new PropositionSymbol("P"));
private final Literal LITERAL_NOT_P = new Literal(new PropositionSymbol("P"), false);
private final Literal LITERAL_Q = new Literal(new PropositionSymbol("Q"));
private final Literal LITERAL_NOT_Q = new Literal(new PropositionSymbol("Q"), false);
private final Literal LITERAL_R = new Literal(new PropositionSymbol("R"));
@Test
public void testAlwaysFalseLiteralsExcludedOnConstruction() {
Clause clause = new Clause();
Assert.assertEquals(0, clause.getNumberLiterals());
clause = new Clause(LITERAL_P);
Assert.assertEquals(1, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.FALSE));
Assert.assertEquals(1, clause.getNumberLiterals());
Assert.assertEquals(Util.createSet(LITERAL_P), clause.getLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.TRUE, false));
Assert.assertEquals(1, clause.getNumberLiterals());
Assert.assertEquals(Util.createSet(LITERAL_P), clause.getLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.FALSE, false));
Assert.assertEquals(2, clause.getNumberLiterals());
Assert.assertEquals(Util.createSet(LITERAL_P, new Literal(PropositionSymbol.FALSE, false)), clause.getLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.TRUE));
Assert.assertEquals(2, clause.getNumberLiterals());
Assert.assertEquals(Util.createSet(LITERAL_P, new Literal(PropositionSymbol.TRUE)), clause.getLiterals());
}
@Test
public void testIsFalse() {
Clause clause = new Clause();
Assert.assertTrue(clause.isFalse());
clause = new Clause(LITERAL_P);
Assert.assertFalse(clause.isFalse());
}
@Test
public void testIsEmpty() {
Clause clause = new Clause();
Assert.assertTrue(clause.isEmpty());
clause = new Clause(LITERAL_P);
Assert.assertFalse(clause.isEmpty());
}
@Test
public void testIsUnitClause() {
Clause clause = new Clause();
Assert.assertFalse(clause.isUnitClause());
clause = new Clause(LITERAL_P);
Assert.assertTrue(clause.isUnitClause());
clause = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertFalse(clause.isUnitClause());
}
@Test
public void testIsDefiniteClause() {
Clause clause = new Clause();
Assert.assertFalse(clause.isDefiniteClause());
clause = new Clause(LITERAL_P);
Assert.assertTrue(clause.isDefiniteClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q);
Assert.assertTrue(clause.isDefiniteClause());
clause = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertFalse(clause.isDefiniteClause());
}
@Test
public void testIsImplicationDefiniteClause() {
Clause clause = new Clause();
Assert.assertFalse(clause.isImplicationDefiniteClause());
clause = new Clause(LITERAL_P);
Assert.assertFalse(clause.isImplicationDefiniteClause());
clause = new Clause(LITERAL_NOT_P);
Assert.assertFalse(clause.isImplicationDefiniteClause());
clause = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertFalse(clause.isImplicationDefiniteClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q);
Assert.assertTrue(clause.isImplicationDefiniteClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_NOT_Q);
Assert.assertTrue(clause.isImplicationDefiniteClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_Q, LITERAL_NOT_Q);
Assert.assertFalse(clause.isImplicationDefiniteClause());
}
@Test
public void testIsHornClause() {
Clause clause = new Clause();
Assert.assertFalse(clause.isHornClause());
clause = new Clause(LITERAL_P);
Assert.assertTrue(clause.isHornClause());
clause = new Clause(LITERAL_NOT_P);
Assert.assertTrue(clause.isHornClause());
clause = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertFalse(clause.isHornClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q);
Assert.assertTrue(clause.isHornClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_NOT_Q);
Assert.assertTrue(clause.isHornClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_Q, LITERAL_NOT_Q);
Assert.assertFalse(clause.isHornClause());
}
@Test
public void testIsGoalClause() {
Clause clause = new Clause();
Assert.assertFalse(clause.isGoalClause());
clause = new Clause(LITERAL_P);
Assert.assertFalse(clause.isGoalClause());
clause = new Clause(LITERAL_NOT_P);
Assert.assertTrue(clause.isGoalClause());
clause = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertFalse(clause.isGoalClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q);
Assert.assertFalse(clause.isGoalClause());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_NOT_Q);
Assert.assertFalse(clause.isGoalClause());
clause = new Clause(LITERAL_NOT_P, LITERAL_NOT_Q);
Assert.assertTrue(clause.isGoalClause());
}
@Test
public void testIsTautology() {
Clause clause = new Clause();
Assert.assertFalse(clause.isTautology());
clause = new Clause(LITERAL_P);
Assert.assertFalse(clause.isTautology());
clause = new Clause(LITERAL_NOT_P);
Assert.assertFalse(clause.isTautology());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.TRUE), LITERAL_R);
Assert.assertTrue(clause.isTautology());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.FALSE, false), LITERAL_R);
Assert.assertTrue(clause.isTautology());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.TRUE, false), LITERAL_R);
Assert.assertFalse(clause.isTautology());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.FALSE), LITERAL_R);
Assert.assertFalse(clause.isTautology());
clause = new Clause(LITERAL_P, LITERAL_Q, LITERAL_R, LITERAL_NOT_Q);
Assert.assertTrue(clause.isTautology());
clause = new Clause(LITERAL_P, LITERAL_Q, LITERAL_R);
Assert.assertFalse(clause.isTautology());
}
@Test
public void testGetNumberLiterals() {
Clause clause = new Clause();
Assert.assertEquals(0, clause.getNumberLiterals());
clause = new Clause(LITERAL_P);
Assert.assertEquals(1, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.FALSE));
Assert.assertEquals(1, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.TRUE, false));
Assert.assertEquals(1, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.FALSE, false));
Assert.assertEquals(2, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, new Literal(PropositionSymbol.TRUE));
Assert.assertEquals(2, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, LITERAL_P);
Assert.assertEquals(1, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertEquals(2, clause.getNumberLiterals());
clause = new Clause(LITERAL_P, LITERAL_Q, LITERAL_R);
Assert.assertEquals(3, clause.getNumberLiterals());
}
@Test
public void testGetNumberPositiveLiterals() {
Clause clause = new Clause();
Assert.assertEquals(0, clause.getNumberPositiveLiterals());
clause = new Clause(LITERAL_P);
Assert.assertEquals(1, clause.getNumberPositiveLiterals());
clause = new Clause(LITERAL_NOT_P);
Assert.assertEquals(0, clause.getNumberPositiveLiterals());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_Q);
Assert.assertEquals(2, clause.getNumberPositiveLiterals());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q, LITERAL_R);
Assert.assertEquals(2, clause.getNumberPositiveLiterals());
}
@Test
public void testGetNumberNegativeLiterals() {
Clause clause = new Clause();
Assert.assertEquals(0, clause.getNumberNegativeLiterals());
clause = new Clause(LITERAL_P);
Assert.assertEquals(0, clause.getNumberNegativeLiterals());
clause = new Clause(LITERAL_NOT_P);
Assert.assertEquals(1, clause.getNumberNegativeLiterals());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_Q);
Assert.assertEquals(1, clause.getNumberNegativeLiterals());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q, LITERAL_R);
Assert.assertEquals(1, clause.getNumberNegativeLiterals());
clause = new Clause(LITERAL_P, LITERAL_NOT_P, LITERAL_NOT_Q);
Assert.assertEquals(2, clause.getNumberNegativeLiterals());
}
@Test
public void testGetLiterals() {
Clause clause = new Clause();
Assert.assertEquals(new HashSet<Literal>(), clause.getLiterals());
clause = new Clause(LITERAL_P);
Assert.assertEquals(Util.createSet(LITERAL_P), clause.getLiterals());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q, LITERAL_R);
Assert.assertEquals(Util.createSet(LITERAL_P, LITERAL_NOT_Q, LITERAL_R), clause.getLiterals());
}
@Test
public void testGetPositiveSymbols() {
Clause clause = new Clause();
Assert.assertEquals(new HashSet<PropositionSymbol>(), clause.getPositiveSymbols());
clause = new Clause(LITERAL_P);
Assert.assertEquals(Util.createSet(new PropositionSymbol("P")), clause.getPositiveSymbols());
clause = new Clause(LITERAL_P, LITERAL_NOT_Q, LITERAL_R);
Assert.assertEquals(Util.createSet(new PropositionSymbol("P"), new PropositionSymbol("R")), clause.getPositiveSymbols());
}
@Test
public void testGetNegativeSymbols() {
Clause clause = new Clause();
Assert.assertEquals(new HashSet<PropositionSymbol>(), clause.getNegativeSymbols());
clause = new Clause(LITERAL_NOT_P);
Assert.assertEquals(Util.createSet(new PropositionSymbol("P")), clause.getNegativeSymbols());
clause = new Clause(LITERAL_NOT_P, LITERAL_NOT_Q, LITERAL_R);
Assert.assertEquals(Util.createSet(new PropositionSymbol("P"), new PropositionSymbol("Q")), clause.getNegativeSymbols());
}
@Test
public void testToString() {
Clause clause = new Clause();
Assert.assertEquals("{}", clause.toString());
clause = new Clause(LITERAL_P);
Assert.assertEquals("{P}", clause.toString());
clause = new Clause(LITERAL_P, LITERAL_Q, LITERAL_R);
Assert.assertEquals("{P, Q, R}", clause.toString());
clause = new Clause(LITERAL_NOT_P, LITERAL_NOT_Q, LITERAL_R);
Assert.assertEquals("{~P, ~Q, R}", clause.toString());
}
@Test
public void testEquals() {
Clause clause1 = new Clause();
Clause clause2 = new Clause();
Assert.assertTrue(clause1.equals(clause2));
clause1 = new Clause(LITERAL_P);
clause2 = new Clause(LITERAL_P);
Assert.assertTrue(clause1.equals(clause2));
clause1 = new Clause(LITERAL_P, LITERAL_Q);
clause2 = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertTrue(clause1.equals(clause2));
clause1 = new Clause(LITERAL_R, LITERAL_P, LITERAL_Q);
clause2 = new Clause(LITERAL_P, LITERAL_Q, LITERAL_R);
Assert.assertTrue(clause1.equals(clause2));
clause1 = new Clause(LITERAL_P);
clause2 = new Clause(LITERAL_Q);
Assert.assertFalse(clause1.equals(clause2));
clause1 = new Clause(LITERAL_P, LITERAL_Q);
clause2 = new Clause(LITERAL_P, LITERAL_R);
Assert.assertFalse(clause1.equals(clause2));
clause1 = new Clause(LITERAL_P);
Assert.assertFalse(clause1.equals(LITERAL_P));
}
@Test
public void testHashCode() {
Clause clause1 = new Clause();
Clause clause2 = new Clause();
Assert.assertTrue(clause1.hashCode() == clause2.hashCode());
clause1 = new Clause(LITERAL_P);
clause2 = new Clause(LITERAL_P);
Assert.assertTrue(clause1.hashCode() == clause2.hashCode());
clause1 = new Clause(LITERAL_P, LITERAL_Q);
clause2 = new Clause(LITERAL_P, LITERAL_Q);
Assert.assertTrue(clause1.hashCode() == clause2.hashCode());
clause1 = new Clause(LITERAL_R, LITERAL_P, LITERAL_Q);
clause2 = new Clause(LITERAL_P, LITERAL_Q, LITERAL_R);
Assert.assertTrue(clause1.hashCode() == clause2.hashCode());
clause1 = new Clause(LITERAL_P);
clause2 = new Clause(LITERAL_Q);
Assert.assertFalse(clause1.hashCode() == clause2.hashCode());
clause1 = new Clause(LITERAL_P, LITERAL_Q);
clause2 = new Clause(LITERAL_P, LITERAL_R);
Assert.assertFalse(clause1.hashCode() == clause2.hashCode());
}
@Test(expected=UnsupportedOperationException.class)
public void testLiteralsImmutable() {
Clause clause = new Clause(LITERAL_P);
clause.getLiterals().add(LITERAL_Q);
}
@Test(expected=UnsupportedOperationException.class)
public void testPostivieSymbolsImmutable() {
Clause clause = new Clause(LITERAL_P);
clause.getPositiveSymbols().add(new PropositionSymbol("Q"));
}
@Test(expected=UnsupportedOperationException.class)
public void testNegativeSymbolsImmutable() {
Clause clause = new Clause(LITERAL_P);
clause.getNegativeSymbols().add(new PropositionSymbol("Q"));
}
}