Giter Site home page Giter Site logo

plogic's Introduction

Plogic

Propositional logic evaluator and pattern transformer written in Rust. Plogic evaluates logic expressions in a REPL (Read, Execute, Print, Loop) environment and generates every truth table necessary to derive the final truth table result. Another use-case of Plogic is to define and apply pattern rules to transform a expression into another expression. This is a common operation in proof systems. Plogic is a very basic version of a proof system.

This project is build purely out of recreational and educational purposes.

Getting started

To build the binary executable, cargo is required alongside the Rust installation.

$ git clone https://github.com/Janko-dev/plogic.git
$ cd plogic
$ cargo build --release

Go to target/release/ to find the plogic.exe (on windows). Run the executable to enter the REPL environment.

$ cargo run --release
Welcome to the REPL of Plogic.
Usage:
   ----------------------------------------
   | And oprator      |  '&'  | 'and'     |
   | Or oprator       |  '|'  | 'or'      |
   | Not oprator      |  '~'  | 'not'     |
   | Cond oprator     |  '->' | 'implies' |
   | Bi-Cond oprator  | '<->' | 'equiv'   |
   ----------------------------------------
   -----------------------------------------------------------------------
   | Rule       |  ':='  | identifier-name := lhs-pattern = rhs-pattern  |
   | binding    | 'rule' | example:   commutative := p & q = q & p       |
   -----------------------------------------------------------------------
   | Rule       |  '=>'  | inline pattern: A & B => p & q = q & p        |
   | Derivation |        | bound pattern : A & B => commutative          |
   -----------------------------------------------------------------------
   - help:   usage info
   - ans:    previous answer
   - toggle: toggle between (T/F) and (1/0) in truth tables
   - quit:   exit repl
> p & q
---------------------
[ q ] [ p ] [ p & q ]
|---| |---| |-------|
| 0 | | 0 | |   0   |
| 1 | | 0 | |   0   |
| 0 | | 1 | |   0   |
| 1 | | 1 | |   1   |
---------------------
>

Grammar

The following grammar describes the parsing strategy to build the abstract syntax tree. It is noteworthy to mention that the usual mathematical symbols for the operators are not used. Instead, the operators come from the bitwise operators found in various programming languages and optional keywords which may be used for the sake of convenience. The table below shows what each operator means.

Operator Meaning
& or and The and-operator which says that both left-hand side and right-hand side should evaluate to true, for the result to equal true as well.
| or or The or-operator which says that either or both left-hand side and right-hand side should evaluate to true, for the result to equal true as well.
~ or not The negation-operator flips true to false and false to true.
-> or implies The conditional implication-operator only evaluates to false when the left-hand side is true and the right-hand side is false, otherwise the result is true.
<-> or equiv The biconditional implication-operator only evaluates to true when both left and right hand sides are equal to eachother.

Rule-based pattern matching

Furthermore, to pattern match expressions and transform them into other expressions, the => or rule keyword is used after a valid propositional expression. Thereafter must follow a valid left hand-side expression, then a =, and then a valid right hand-side expression. Example:

A & (B | C) => p & (q | r) = (p & q) | (p & r)

This expression describes the following. The expression A & (B | C) will be matched against the left hand-side after =>, i.e. p & (q | r). Since both have the same pattern, it is a valid match. Thereafter, the right hand-side will be substituted according to the matched symbols in the left hand-side. Therefore, producing the following result:

(A & B) | (A & C)

In the case that the left hand-side did not match the expression, an attempt will be made to match the right hand side instead. The same procedure for pattern matching applies, only in reverse. Now, the right hand-side is matched, then substituted in the left hand-side of the given rule. An example will make this more clear. Consider the 'almost' same expression:

(A & B) | (A & C) => p & (q | r) = (p & q) | (p & r)

Notice that the left hand-side of the rule portion p & (q | r) does not match the sub-expression (A & B) | (A & C). Therefore, the right hand-side will be attempted to match, which produces the result:

A & (B | C)

Aside from using inline rule patterns as demonstrated above, which can get convoluted to type if the given rule pattern is used multiple times, there is also the possibility to bind a rule to an identifier name. Consider the following:

distributive := p & (q | r) = (p & q) | (p & r)

the identifier name distributive is now bound to the pattern given after :=. The pattern identifier can now be used instead. i.e.,

A & (B | C) => distributive

which produces the same result as before, i.e., (A & B) | (A & C).

Expression       = Rule_binding | Rule_apply ;
Rule_binding     = Atom ":=" Bi_conditional "=" Bi_conditional ;
Rule_apply       = Bi_conditional ("=>" Bi_conditional "=" Bi_conditional)? ;
Bi_conditional   = Conditional (("<->") Conditional)* ;
Conditional      = Or (("->") Or)* ;
Or               = And (("|") And)* ;
And              = Negation (("&") Negation)* ;
Negation         = "~" Negation | Primary ;
Primary          = Atom | "(" Bi_conditional ")" ;
Atom             = ["a"-"z" | "A"-"Z"]* ;

More Examples

> A & ~A
-----------------------
[ A ] [ ~A ] [ A & ~A ]
|---| |----| |--------|
| 0 | | 1  | |   0    |
| 1 | | 0  | |   0    |
-----------------------
> (p implies q) and (q implies p) 
-----------------------------------------------------------------------------------
[ q ] [ p ] [ (q -> p) ] [ (p -> q) ] [ q -> p ] [ p -> q ] [ (p -> q) & (q -> p) ]
|---| |---| |----------| |----------| |--------| |--------| |---------------------|
| 0 | | 0 | |    1     | |    1     | |   1    | |   1    | |          1          |
| 1 | | 0 | |    0     | |    1     | |   0    | |   1    | |          0          |
| 0 | | 1 | |    1     | |    0     | |   1    | |   0    | |          0          |
| 1 | | 1 | |    1     | |    1     | |   1    | |   1    | |          1          |
-----------------------------------------------------------------------------------
> A & (B | C) => p & (q | r) = (p & q) | (p & r)
(A & B) | (A & C)
> ans
-----------------------------------------------------------
[ C ] [ B ] [ A ] [ A & C ] [ A & B ] [ (A & B) | (A & C) ]
|---| |---| |---| |-------| |-------| |-------------------|
| 0 | | 0 | | 0 | |   0   | |   0   | |         0         |
| 0 | | 0 | | 1 | |   0   | |   0   | |         0         |
| 0 | | 1 | | 0 | |   0   | |   0   | |         0         |
| 0 | | 1 | | 1 | |   0   | |   1   | |         1         |
| 1 | | 0 | | 0 | |   0   | |   0   | |         0         |
| 1 | | 0 | | 1 | |   1   | |   0   | |         1         |
| 1 | | 1 | | 0 | |   0   | |   0   | |         0         |
| 1 | | 1 | | 1 | |   1   | |   1   | |         1         |
-----------------------------------------------------------
>
> DeMorgan := ~(p & q) = ~p | ~q      
> ~((a -> b) & ~(b -> c)) => DeMorgan
~(a -> b) | ~~(b -> c)
> toggle
Changed truthtable symbols from '1'/'0' to 'T'/'F'
> ans
-------------------------------------------------------------------------------------------------------------
[ c ] [ b ] [ a ] [ ~(b -> c) ] [ ~(a -> b) ] [ ~~(b -> c) ] [ b -> c ] [ a -> b ] [ ~(a -> b) | ~~(b -> c) ]
|---| |---| |---| |-----------| |-----------| |------------| |--------| |--------| |------------------------|
| F | | F | | F | |     F     | |     F     | |     T      | |   T    | |   T    | |           T            |
| F | | F | | T | |     F     | |     T     | |     T      | |   T    | |   F    | |           T            |
| F | | T | | F | |     T     | |     F     | |     F      | |   F    | |   T    | |           F            |
| F | | T | | T | |     T     | |     F     | |     F      | |   F    | |   T    | |           F            |
| T | | F | | F | |     F     | |     F     | |     T      | |   T    | |   T    | |           T            |
| T | | F | | T | |     F     | |     T     | |     T      | |   T    | |   F    | |           T            |
| T | | T | | F | |     F     | |     F     | |     T      | |   T    | |   T    | |           T            |
| T | | T | | T | |     F     | |     F     | |     T      | |   T    | |   T    | |           T            |
-------------------------------------------------------------------------------------------------------------

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.