Initial data commit
This commit is contained in:
parent
72d218235f
commit
f23f22d71c
199087 changed files with 3378941 additions and 0 deletions
89
Task/Truth-table/D/truth-table.d
Normal file
89
Task/Truth-table/D/truth-table.d
Normal file
|
|
@ -0,0 +1,89 @@
|
|||
import std.stdio, std.string, std.array, std.algorithm, std.typecons;
|
||||
|
||||
struct Var {
|
||||
const char name;
|
||||
bool val;
|
||||
}
|
||||
const string expr;
|
||||
Var[] vars;
|
||||
|
||||
bool pop(ref bool[] arr) pure nothrow {
|
||||
const last = arr.back;
|
||||
arr.popBack;
|
||||
return last;
|
||||
}
|
||||
|
||||
enum isOperator = (in char c) pure => "&|!^".canFind(c);
|
||||
|
||||
enum varsCountUntil = (in char c) nothrow =>
|
||||
.vars.map!(v => v.name).countUntil(c).Nullable!(int, -1);
|
||||
|
||||
bool evalExp() {
|
||||
bool[] stack;
|
||||
|
||||
foreach (immutable e; .expr) {
|
||||
if (e == 'T')
|
||||
stack ~= true;
|
||||
else if (e == 'F')
|
||||
stack ~= false;
|
||||
else if (!e.varsCountUntil.isNull)
|
||||
stack ~= .vars[e.varsCountUntil.get].val;
|
||||
else switch (e) {
|
||||
case '&':
|
||||
stack ~= stack.pop & stack.pop;
|
||||
break;
|
||||
case '|':
|
||||
stack ~= stack.pop | stack.pop;
|
||||
break;
|
||||
case '!':
|
||||
stack ~= !stack.pop;
|
||||
break;
|
||||
case '^':
|
||||
stack ~= stack.pop ^ stack.pop;
|
||||
break;
|
||||
default:
|
||||
throw new Exception("Non-conformant character '" ~
|
||||
e ~ "' in expression.");
|
||||
}
|
||||
}
|
||||
|
||||
assert(stack.length == 1);
|
||||
return stack.back;
|
||||
}
|
||||
|
||||
void setVariables(in size_t pos)
|
||||
in {
|
||||
assert(pos <= .vars.length);
|
||||
} body {
|
||||
if (pos == .vars.length)
|
||||
return writefln("%-(%s %) %s",
|
||||
.vars.map!(v => v.val ? "T" : "F"),
|
||||
evalExp ? "T" : "F");
|
||||
|
||||
.vars[pos].val = false;
|
||||
setVariables(pos + 1);
|
||||
.vars[pos].val = true;
|
||||
setVariables(pos + 1);
|
||||
}
|
||||
|
||||
static this() {
|
||||
"Accepts single-character variables (except for 'T' and 'F',
|
||||
which specify explicit true or false values), postfix, with
|
||||
&|!^ for and, or, not, xor, respectively; optionally
|
||||
seperated by whitespace.".writeln;
|
||||
|
||||
"Boolean expression: ".write;
|
||||
.expr = readln.split.join;
|
||||
}
|
||||
|
||||
void main() {
|
||||
foreach (immutable e; expr)
|
||||
if (!e.isOperator && !"TF".canFind(e) &&
|
||||
e.varsCountUntil.isNull)
|
||||
.vars ~= Var(e);
|
||||
if (.vars.empty)
|
||||
return;
|
||||
|
||||
writefln("%-(%s %) %s", .vars.map!(v => v.name), .expr);
|
||||
setVariables(0);
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue