Search code examples
perlopenoffice-writerodt

print truth table in to odt file


i want to print truth table in to a table in an adt file, t got a program but i don know how to get vale or value to print to odt file, this program just print result on screen !

sub truth_table {
    my $s = shift;
    #print "$s\n";
    my  @vars;
    for ($s =~ /([a-zA-Z_]\w*)/g) {
        push @vars, $_ ;

    }
    #print "$s\n";
    #print "$_\n";
    #print Dumper \@vars;
    #print "\n", join("\t", @vars, $s), "\n", '-' x 40, "\n";
    #print Dumper \@vars;
    @vars = map("\$$_", @vars);
    $s =~ s/([a-zA-Z_]\w*)/\$$1/g;
    $s = "print(".join(',"\t",', map("($_?'1':'0')", @vars, $s)).",\"\\n\")";
    $s = "for my $_ (0, 1) { $s }" for (reverse @vars);
    eval $s;
}
truth_table 'A ^ A_1';

Solution

  • Get the result of eval with Capture::Tiny, then split the string into a two-dimensional array based on https://stackoverflow.com/a/4226073/5100564.

    use Capture::Tiny 'capture_stdout';
    
    sub truth_table {
        #...the rest of your code here...
        my $stdout = capture_stdout {
            eval $s;
        };
        return $stdout;
    }
    $truth_string = truth_table 'A ^ A_1';
    my @truth_array;
    foreach my $line (split "\n", $truth_string) {
        push @truth_array, [split ' ', $line];
    }
    foreach my $line (@truth_array) {
        foreach my $val (@$line) {
            print $val;
        }
        print "\n";
    }
    

    For this to work, I executed the following commands based on What's the easiest way to install a missing Perl module?

    cpan
    install Capture::Tiny
    

    However, I would solve this problem in LibreOffice with a Python macro instead. APSO makes it convenient to enter and run this code.

    import uno
    from itertools import product
    
    def truth_table():
        NUM_VARS = 2  # A and B
        columns = NUM_VARS + 1
        rows = pow(2, NUM_VARS) + 1
        oDoc = XSCRIPTCONTEXT.getDocument()
        oText = oDoc.getText()
        oCursor = oText.createTextCursorByRange(oText.getStart())
        oTable = oDoc.createInstance("com.sun.star.text.TextTable")
        oTable.initialize(rows, columns)
        oText.insertTextContent(oCursor, oTable, False)
        for column, heading in enumerate(("A", "B", "A ^ B")):
            oTable.getCellByPosition(column, 0).setString(heading)
        row = 1  # the second row
        for p in product((0, 1), repeat=NUM_VARS):
            result = truth_function(*p)
            for column in range(NUM_VARS):
                oTable.getCellByPosition(column, row).setString(p[column])
            oTable.getCellByPosition(column + 1, row).setString(result)
            row += 1
    
    def truth_function(x, y):
        return pow(x, y);
    
    g_exportedScripts = truth_table,
    

    enter image description here

    Using product in this way is based on Creating a truth table for any expression in Python.

    More documentation for Python-UNO can be found at https://wiki.openoffice.org/wiki/Python.