I’m trying to write a macro to generate truth tables. So far I’ve had success with finding the variables and evaluating the expression. However, I haven’t been able to display the truth value for individual variables.
The code I have so far is the following:
macro truth_table(expr)
# Walk the expression and push the variables found to a vector `vars`:
vars = Vector{Symbol}([])
find_vars!(var::Symbol) = !(var in vars) && push!(vars, var)
find_vars!(expr::Expr) = find_vars!.(expr.args)
find_vars!(::Bool) = nothing
find_vars!(expr)
# Generate nested for loops where each variable is given a truth value:
ex = :(@show $vars, $expr) # <- the problematic line (I think?)
for i in reverse(vars) # Take a variable (in the order they were found).
ex = quote
for $i in [true, false] # Iterate over truth values.
$ex # Nest the previous expression.
end
end
end
return ex
end # truth_table
This will correctly evaluate truth values for arbitrary boolean expressions, but in the REPL it’ll print as:
julia> @truth_table x && y
([:x, :y], x && y) = ([:x, :y], true)
([:x, :y], x && y) = ([:x, :y], false)
([:x, :y], x && y) = ([:x, :y], false)
([:x, :y], x && y) = ([:x, :y], false)
I would expect the RHS to be ([true, true], true)
, ([true, false], false)
and so on.
My question is: how can I show the evaluated value for each variable? I know vars
is an array of symbols, but I’d like to get whatever the symbol evaluates to. What should I write in the intial ex
instead?
Ideally I would like to save the table in a NamedArray where the column names are the names of each variable, but for now I’m just trying to get it to print correctly.