Skip to content

Commit

Permalink
perf: optimize truth table
Browse files Browse the repository at this point in the history
  • Loading branch information
luisfbl committed Oct 29, 2023
1 parent 4c96796 commit 0e86060
Show file tree
Hide file tree
Showing 9 changed files with 79 additions and 75 deletions.
1 change: 0 additions & 1 deletion requirements.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,2 @@
pyinstaller
texttable
colorama
2 changes: 1 addition & 1 deletion src/data/decode.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@


def decode_expression(expr):
if isinstance(expr, Operator) or isinstance(expr, Negation):
if isinstance(expr, Base):
return str(expr)
else:
return expr
2 changes: 1 addition & 1 deletion src/data/encode.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ def encode_expression(expr: str) -> Base:
i += 1
# Append if char is a real preposition, like: P, Q, R. Ignore 'v' because it's an operator
elif expr[i] != 'v' and expr[i].isalpha():
result.append(expr[i].upper())
result.append(Preposition(expr[i].upper()))
i += 1
else:
# The operator with the most characters is <-> (3), so the substring
Expand Down
4 changes: 4 additions & 0 deletions src/entity/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,7 @@ def __eq__(self, other):
return all(getattr(self, attr) == getattr(other, attr) for attr in vars(self) if not attr.startswith('_'))

return False

def __hash__(self):
# Implement a custom hash method for instances of this class
return hash(tuple(sorted(self.__dict__.items())))
8 changes: 8 additions & 0 deletions src/entity/operators.py
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,14 @@ def __str__(self):
return f'~{expr_str}'


class Preposition(Base):
def __init__(self, prep):
self.prep = prep

def __str__(self):
return f'{self.prep}'


operators = {
'^': Conjunction,
'v': Disjunction,
Expand Down
13 changes: 6 additions & 7 deletions src/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

from data.encode import encode_expression
from truth_table.table import generate_combinations, evaluate_expressions, table_type
from src.entity.operators import *


def print_main_header():
Expand All @@ -25,7 +26,7 @@ def get_menu_choice():
return int(input("Escolha uma opção: "))


def parse_input(item, prepositions, expressions,):
def parse_input(item, prepositions, expressions, ):
wrapped = encode_expression(item)

if wrapped is None:
Expand Down Expand Up @@ -74,14 +75,11 @@ def main():
if menu == 1:
combinations = generate_combinations(prepositions)
values = evaluate_expressions(prepositions, expressions, combinations)
expanded_expressions = [result.pop(0) for result in values]
expanded_expressions = values.keys()

# Orients values in rows
rows = list(zip(*values))
# Adds the preposition rows to the results
rows = [list(combinations[i]) + list(rows[i]) for i in range(len(rows))] if rows else combinations

header = prepositions + list(map(lambda x: str(x), expanded_expressions))
rows = list(zip(*values.values()))
header = list(map(lambda x: str(x), expanded_expressions))
results = [['V' if value else 'F' for value in row] for row in rows]

table = Texttable()
Expand All @@ -91,6 +89,7 @@ def main():

print(table.draw())
print(f'Tipo de tabela: {table_type(rows)}')
break
else:
break

Expand Down
8 changes: 4 additions & 4 deletions src/tests/data/test_decode.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,22 +8,22 @@ class TestDecode(unittest.TestCase):
def test_decode_conjunction(self):
self.assertEqual(
"P^Q",
decode_expression(Conjunction(left='P', right='Q'))
decode_expression(Conjunction(left=Preposition(prep='P'), right=Preposition('Q')))
)

self.assertEqual(
"(A^B)^C",
decode_expression(Conjunction(left=Conjunction(left='A', right='B'), right='C'))
decode_expression(Conjunction(left=Conjunction(left=Preposition(prep='A'), right=Preposition(prep='B')), right=Preposition(prep='C')))
)

self.assertEqual(
"((D^E)^F)^G",
decode_expression(Conjunction(left=Conjunction(left=Conjunction(left='D', right='E'), right='F'), right='G'))
decode_expression(Conjunction(left=Conjunction(left=Conjunction(left=Preposition(prep='D'), right=Preposition(prep='E')), right=Preposition(prep='F')), right=Preposition(prep='G')))
)

self.assertEqual(
"(((H^I)^J)^K)^L",
decode_expression(Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left='H', right='I'), right='J'), right='K'), right='L'))
decode_expression(Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left=Preposition(prep='H'), right=Preposition(prep='I')), right=Preposition(prep='J')), right=Preposition(prep='K')), right=Preposition(prep='L')))
)

self.assertEqual(
Expand Down
53 changes: 26 additions & 27 deletions src/tests/data/test_encode.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,137 +7,136 @@
class TestEncode(unittest.TestCase):
def test_encode_conjunction(self):
self.assertEqual(
Conjunction(left='P', right='Q'),
Conjunction(left=Preposition(prep='P'), right=Preposition('Q')),
encode_expression("(P^Q)")
)

self.assertEqual(
Conjunction(left=Conjunction(left='A', right='B'), right='C'),
Conjunction(left=Conjunction(left=Preposition(prep='A'), right=Preposition(prep='B')), right=Preposition(prep='C')),
encode_expression("((A^B)^C)")
)

self.assertEqual(
Conjunction(left=Conjunction(left=Conjunction(left='D', right='E'), right='F'), right='G'),
Conjunction(left=Conjunction(left=Conjunction(left=Preposition(prep='D'), right=Preposition(prep='E')), right=Preposition(prep='F')), right=Preposition(prep='G')),
encode_expression("(((D^E)^F)^G)")
)

self.assertEqual(
Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left='H', right='I'), right='J'), right='K'), right='L'),
Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left=Preposition(prep='H'), right=Preposition(prep='I')), right=Preposition(prep='J')), right=Preposition(prep='K')), right=Preposition(prep='L')),
encode_expression("((((H^I)^J)^K)^L)")
)

self.assertEqual(
Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left='M', right='N'), right='O'), right='P'), right='Q'), right='R'),
Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left=Conjunction(left=Preposition(prep='M'), right=Preposition(prep='N')), right=Preposition(prep='O')), right=Preposition(prep='P')), right=Preposition(prep='Q')), right=Preposition(prep='R')),
encode_expression("(((((M^N)^O)^P)^Q)^R)")
)

def test_encode_disjunction(self):
self.assertEqual(
Disjunction(left='P', right='Q'),
Disjunction(left=Preposition(prep='P'), right=Preposition(prep='Q')),
encode_expression("PvQ")
)

self.assertEqual(
Disjunction(left=Disjunction(left='A', right='B'), right='C'),
Disjunction(left=Disjunction(left=Preposition(prep='A'), right=Preposition(prep='B')), right=Preposition(prep='C')),
encode_expression("((AvB)vC)")
)

self.assertEqual(
Disjunction(left='D', right=Disjunction(left='E', right='F')),
Disjunction(left=Preposition(prep='D'), right=Disjunction(left=Preposition(prep='E'), right=Preposition(prep='F'))),
encode_expression("Dv(EvF)")
)

self.assertEqual(
Disjunction(left=Disjunction(left=Disjunction(left=Disjunction(left='P', right='Q'), right=Disjunction(left='R', right=Disjunction(left='S', right='T'))), right=Disjunction(left='U', right=Disjunction(left='V', right=Disjunction(left='W', right=Disjunction(left='X', right='Y'))))), right='Z'),
Disjunction(left=Disjunction(left=Disjunction(left=Disjunction(left=Preposition(prep='P'), right=Preposition(prep='Q')), right=Disjunction(left=Preposition(prep='R'), right=Disjunction(left=Preposition(prep='S'), right=Preposition(prep='T')))), right=Disjunction(left=Preposition(prep='U'), right=Disjunction(left=Preposition(prep='V'), right=Disjunction(left=Preposition(prep='W'), right=Disjunction(left=Preposition(prep='X'), right=Preposition(prep='Y')))))), right=Preposition(prep='Z')),
encode_expression("(((PvQ)v(Rv(SvT)))v(Uv(Vv(Wv(XvY)))))vZ")
)

self.assertEqual(
Disjunction(left=Disjunction(left=Disjunction(left='J', right='K'), right='L'), right='M'),
Disjunction(left=Disjunction(left=Disjunction(left=Preposition(prep='J'), right=Preposition(prep='K')), right=Preposition(prep='L')), right=Preposition(prep='M')),
encode_expression("((JvK)vL)vM")
)

def test_encode_conditional(self):
self.assertEqual(
Conditional(left='P', right='Q'),
Conditional(left=Preposition(prep='P'), right=Preposition(prep='Q')),
encode_expression("P->Q")
)

self.assertEqual(
Conditional(left=Conditional(left=Conditional(left='P', right=Conditional(left='R', right=Conditional(left='T', right='V'))), right=Conditional(left='R', right='G')), right='R'),
Conditional(left=Conditional(left=Conditional(left=Preposition(prep='P'), right=Conditional(left=Preposition(prep='R'), right=Conditional(left=Preposition(prep='T'), right=Preposition(prep='V')))), right=Conditional(left=Preposition(prep='R'), right=Preposition(prep='G'))), right=Preposition(prep='R')),
encode_expression("((P->(R->(T->V)))->(R->G))->R")
)

self.assertEqual(
Conditional(left=Conditional(left=Conditional(left='A', right=Conditional(left='B', right='C')), right=Conditional(left='D', right=Conditional(left='E', right='F'))), right='G'),
Conditional(left=Conditional(left=Conditional(left=Preposition(prep='A'), right=Conditional(left=Preposition(prep='B'), right=Preposition(prep='C'))), right=Conditional(left=Preposition(prep='D'), right=Conditional(left=Preposition(prep='E'), right=Preposition(prep='F')))), right=Preposition(prep='G')),
encode_expression("((A->(B->C))->(D->(E->F)))->G")
)

self.assertEqual(
Conditional(left=Conditional(left=Conditional(left=Conditional(left='P', right='Q'), right=Conditional(left='R', right='S')), right=Conditional(left=Conditional(left='T', right='U'), right=Conditional(left='V', right='W'))), right='X'),
Conditional(left=Conditional(left=Conditional(left=Conditional(left=Preposition(prep='P'), right=Preposition(prep='Q')), right=Conditional(left=Preposition(prep='R'), right=Preposition(prep='S'))), right=Conditional(left=Conditional(left=Preposition(prep='T'), right=Preposition(prep='U')), right=Conditional(left=Preposition(prep='V'), right=Preposition(prep='W')))), right=Preposition(prep='X')),
encode_expression("(((P->Q)->(R->S))->((T->U)->(V->W)))->X")
)

self.assertEqual(
Conditional(left=Conditional(left=Conditional(left='P', right='Q'), right=Conditional(left='R', right=Conditional(left='S', right=Conditional(left='T', right=Conditional(left='U', right=Conditional(left='V', right=Conditional(left='W', right=Conditional(left='X', right=Conditional(left='Y', right='Z'))))))))), right=Conditional(left=Conditional(left=Conditional(left='A', right='B'), right=Conditional(left='C', right=Conditional(left='D', right=Conditional(left='E', right=Conditional(left='F', right=Conditional(left='G', right=Conditional(left='H', right='I'))))))), right='J')),
encode_expression("((P->Q)->(R->(S->(T->(U->(V->(W->(X->(Y->Z)))))))))->(((A->B)->(C->(D->(E->(F->(G->(H->I)))))))->J)")
Conditional(left=Conditional(left=Conditional(left=Preposition(prep='P'), right=Preposition(prep='Q')), right=Conditional(left=Preposition(prep='R'), right=Conditional(left=Preposition(prep='S'), right=Conditional(left=Preposition(prep='T'), right=Conditional(left=Preposition(prep='U'), right=Conditional(left=Preposition(prep='V'), right=Conditional(left=Preposition(prep='W'), right=Conditional(left=Preposition(prep='X'), right=Conditional(left=Preposition(prep='Y'), right=Preposition(prep='Z')))))))))), right=Conditional(left=Conditional(left=Conditional(left=Preposition(prep='A'), right=Preposition(prep='B')), right=Conditional(left=Preposition(prep='C'), right=Conditional(left=Preposition(prep='D'), right=Conditional(left=Preposition(prep='E'), right=Conditional(left=Preposition(prep='F'), right=Conditional(left=Preposition(prep='G'), right=Conditional(left=Preposition(prep='H'), right=Preposition(prep='I')))))))), right=Preposition(prep='J'))), encode_expression("((P->Q)->(R->(S->(T->(U->(V->(W->(X->(Y->Z)))))))))->(((A->B)->(C->(D->(E->(F->(G->(H->I)))))))->J)")
)

def test_encode_biconditional(self):
self.assertEqual(
BiConditional(left='P', right='Q'),
BiConditional(left=Preposition(prep='P'), right=Preposition(prep='Q')),
encode_expression("P<->Q")
)

self.assertEqual(
BiConditional(left=BiConditional(left='P', right='Q'), right=BiConditional(left='R', right=BiConditional(left='S', right=BiConditional(left='T', right=BiConditional(left='U', right=BiConditional(left='V', right=BiConditional(left='W', right=BiConditional(left='X', right=BiConditional(left='Y', right='Z'))))))))),
BiConditional(left=BiConditional(left=Preposition(prep='P'), right=Preposition(prep='Q')), right=BiConditional(left=Preposition(prep='R'), right=BiConditional(left=Preposition(prep='S'), right=BiConditional(left=Preposition(prep='T'), right=BiConditional(left=Preposition(prep='U'), right=BiConditional(left=Preposition(prep='V'), right=BiConditional(left=Preposition(prep='W'), right=BiConditional(left=Preposition(prep='X'), right=BiConditional(left=Preposition(prep='Y'), right=Preposition(prep='Z')))))))))),
encode_expression("(P<->Q)<->(R<->(S<->(T<->(U<->(V<->(W<->(X<->(Y<->Z))))))))"),
)

self.assertEqual(
BiConditional(left=BiConditional(left='P', right=BiConditional(left='Q', right=BiConditional(left='R', right=BiConditional(left='S', right=BiConditional(left='T', right='U'))))), right='V'),
BiConditional(left=BiConditional(left=Preposition(prep='P'), right=BiConditional(left=Preposition(prep='Q'), right=BiConditional(left=Preposition(prep='R'), right=BiConditional(left=Preposition(prep='S'), right=BiConditional(left=Preposition(prep='T'), right=Preposition(prep='U')))))), right=Preposition(prep='V')),
encode_expression("(P<->(Q<->(R<->(S<->(T<->U)))))<->V"),
)

self.assertEqual(
BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left='A', right='B'), right='C'), right='D'), right='E'), right='F'), right='G'),
BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=Preposition(prep='A'), right=Preposition(prep='B')), right=Preposition(prep='C')), right=Preposition(prep='D')), right=Preposition(prep='E')), right=Preposition(prep='F')), right=Preposition(prep='G')),
encode_expression("(((((A<->B)<->C)<->D)<->E)<->F)<->G"),
)

self.assertEqual(
BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left='P', right='Q'), right='R'), right='S'), right='T'), right='U'), right='V'), right='W'), right='X'), right='Y'),
BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=BiConditional(left=Preposition(prep='P'), right=Preposition(prep='Q')), right=Preposition(prep='R')), right=Preposition(prep='S')), right=Preposition(prep='T')), right=Preposition(prep='U')), right=Preposition(prep='V')), right=Preposition(prep='W')), right=Preposition(prep='X')), right=Preposition(prep='Y')),
encode_expression("((((((((P<->Q)<->R)<->S)<->T)<->U)<->V)<->W)<->X)<->Y")
)

def test_encode_negation(self):
self.assertEqual(
Negation(expr='P'),
Negation(expr=Preposition(prep='P')),
encode_expression("~P")
)

def test_encode(self):
self.assertEqual(
Conjunction(left=Negation(expr=Disjunction(left=Disjunction(left='P', right='Q'), right=Conditional(left='P', right=Conjunction(left='Q', right='R')))), right=Disjunction(left=BiConditional(left='P', right='R'), right=Conditional(left='T', right='U'))),
Conjunction(left=Negation(expr=Disjunction(left=Disjunction(left=Preposition(prep='P'), right=Preposition(prep='Q')), right=Conditional(left=Preposition(prep='P'), right=Conjunction(left=Preposition(prep='Q'), right=Preposition(prep='R'))))), right=Disjunction(left=BiConditional(left=Preposition(prep='P'), right=Preposition(prep='R')), right=Conditional(left=Preposition(prep='T'), right=Preposition(prep='U')))),
encode_expression("~((PvQ)v(P->(Q^R)))^((P<->R)v(T->U))")
)

self.assertEqual(
Conjunction(left=Disjunction(left='P', right='Q'), right=Negation(expr='P')),
Conjunction(left=Disjunction(left=Preposition(prep='P'), right=Preposition(prep='Q')), right=Negation(expr=Preposition(prep='P'))),
encode_expression("(PvQ)^~P"),
)

self.assertEqual(
Disjunction(left=Negation(expr=Conjunction(left='P', right='Q')), right=Conditional(left=Disjunction(left='R', right='S'), right=BiConditional(left=Disjunction(left='T', right='U'), right=Negation(expr='W')))),
Disjunction(left=Negation(expr=Conjunction(left=Preposition(prep='P'), right=Preposition(prep='Q'))), right=Conditional(left=Disjunction(left=Preposition(prep='R'), right=Preposition(prep='S')), right=BiConditional(left=Disjunction(left=Preposition(prep='T'), right=Preposition(prep='U')), right=Negation(expr=Preposition(prep='W'))))),
encode_expression("~(P^Q)v((RvS)->((TvU)<->~W))")
)

self.assertEqual(
Conjunction(left=Conjunction(left='A', right=Disjunction(left='B', right='C')), right=Conditional(left=Disjunction(left='D', right=Disjunction(left='E', right='F')), right=Conjunction(left=BiConditional(left='G', right=BiConditional(left='H', right='I')), right=Conjunction(left='J', right=Disjunction(left='K', right='L'))))),
Conjunction(left=Conjunction(left=Preposition(prep='A'), right=Disjunction(left=Preposition(prep='B'), right=Preposition(prep='C'))), right=Conditional(left=Disjunction(left=Preposition(prep='D'), right=Disjunction(left=Preposition(prep='E'), right=Preposition(prep='F'))), right=Conjunction(left=BiConditional(left=Preposition(prep='G'), right=BiConditional(left=Preposition(prep='H'), right=Preposition(prep='I'))), right=Conjunction(left=Preposition(prep='J'), right=Disjunction(left=Preposition(prep='K'), right=Preposition(prep='L')))))),
encode_expression("(A^(BvC))^((Dv(EvF))->((G<->(H<->I))^(J^(KvL))))")
)

self.assertEqual(
Negation(expr=Disjunction(left=Negation(expr=Negation(expr=Disjunction(left='P', right='Q'))), right=Conditional(left=Negation(expr=Disjunction(left='R', right='S')), right=Negation(expr=BiConditional(left=Disjunction(left='T', right='U'), right='W'))))),
Negation(expr=Disjunction(left=Negation(expr=Negation(expr=Disjunction(left=Preposition(prep='P'), right=Preposition(prep='Q')))), right=Conditional(left=Negation(expr=Disjunction(left=Preposition(prep='R'), right=Preposition(prep='S'))), right=Negation(expr=BiConditional(left=Disjunction(left=Preposition(prep='T'), right=Preposition(prep='U')), right=Preposition(prep='W')))))),
encode_expression("~(~(~(PvQ))v(~(RvS)->~((TvU)<->W)))")
)

Expand Down
Loading

0 comments on commit 0e86060

Please sign in to comment.