Task: Decision tables


C++: #include <iostream>
#include <string>
#include <vector>

const std::vector<std::pair<std::string, std::string>> conditions = {
    {"Printer prints", "NNNNYYYY"},
    {"A red light is flashing", "YYNNYYNN"},
    {"Printer is recognized by computer", "NYNYNYNY"}
};

const std::vector<std::pair<std::string, std::string>> actions = {
    {"Check the power cable", "NNYNNNNN"},
    {"Check the printer-computer cable", "YNYNNNNN"},
    {"Ensure printer software is installed", "YNYNYNYN"},
    {"Check/replace ink", "YYNNNYNN"},
    {"Check for paper jam", "NYNYNNNN"},
};

int main() {
    const size_t nc = conditions.size();
    const size_t na = actions.size();
    const size_t nr = conditions[0].second.size();
    const int np = 7;

    auto answers = new bool[nc];
    std::string input;

    std::cout << "Please answer the following questions with a y or n:\n";
    for (size_t c = 0; c < nc; c++) {
        char ans;
        do {
            std::cout << conditions[c].first << "? ";

            std::getline(std::cin, input);
            ans = std::toupper(input[0]);
        } while (ans != 'Y' && ans != 'N');
        answers[c] = ans == 'Y';
    }

    std::cout << "Recommended action(s)\n";
    for (size_t r = 0; r < nr; r++) {
        for (size_t c = 0; c < nc; c++) {
            char yn = answers[c] ? 'Y' : 'N';
            if (conditions[c].second[r] != yn) {
                goto outer;
            }
        }
        if (r == np) {
            std::cout << "  None (no problem detected)\n";
        } else {
            for (auto action : actions) {
                if (action.second[r] == 'Y') {
                    std::cout << "  " << action.first << '\n';
                }
            }
        }
        break;

    outer: {}
    }

    delete[] answers;
    return 0;
}






Python: 

def dt_creator():
    print("\n\nCREATING THE DECISION TABLE\n")
    conditions = input("Input conditions, in order, separated by commas: ")
    conditions = [c.strip() for c in conditions.split(',')]
    print( ("\nThat was %s conditions:\n  " % len(conditions))
           + '\n  '.join("%i: %s" % x for x in enumerate(conditions, 1)) )
    print("\nInput an action, a semicolon, then a list of tuples of rules that trigger it. End with a blank line")
    action2rules, action = [], ' '
    while action:
        action = input("%i: " % (len(action2rules) + 1)).strip()
        if action:
            name, _, rules = [x.strip() for x in action.partition(';')]
            rules = eval(rules)
            assert all(len(rule) == len(conditions) for rule in rules), \
                   "The number of conditions in a rule to trigger this action is wrong" 
            action2rules.append((name, rules))
    actions = [x[0] for x in action2rules]
    
    rule2actions = dict((y,[]) for y in set(sum((x[1] for x in action2rules), [])))
    for action, rules in action2rules:
        for r in rules:
            rule2actions[r].append( action )
    return conditions, rule2actions

def dt_user(dt, default=['Pray!']):
    conditions, rule2actions = dt
    print("\n\nUSING THE DECISION TABLE\n")
    rule = tuple(int('y' == input("%s? (Answer y if statement is true or n): " % c)) for c in conditions)
    print("Try this:\n  " + '\n  '.join(rule2actions.get(rule, default)))

if __name__ == '__main__':
    dt = dt_creator()
    dt_user(dt)
    dt_user(dt)
    dt_user(dt)