11. Find a cheapest configuration

Reuse the backup rules (L ∨ R) ∧ (¬R ∨ E). Local storage costs 5, remote storage 2, encryption 1, and notifications 0. To find the cheapest valid choice, evaluate alternatives with minimum and independent choices with addition.

11.1. Define the evaluation

A false branch has infinite cost. A true literal pays its price; a false literal costs zero. A free variable chooses its cheaper sign. The callback interface passes your price array through userdata.

static double impossible(void *data) { (void)data; return INFINITY; }
static double literal_cost(void *data, uint32_t variable, int8_t sign) {
    const double *prices = (const double *)data;
    if (sign == 1) return prices[variable - 1];
    if (sign == 0) return 0;
    return fmin(0, prices[variable - 1]); /* A free variable chooses its cheaper sign. */
}
static double cheaper(void *data, double a, double b) { (void)data; return fmin(a, b); }
static double combined(void *data, double a, double b) { (void)data; return a + b; }

11.2. Evaluate and change prices

The same circuit can be evaluated with another price list. Values here are double; exact probabilities use the separate rational-weight API.

double prices[] = {5, 2, 1, 0};
TididiAlgebra algebra = {prices, impossible, literal_cost, cheaper, combined};
double cost = 0;
check(tididi_evaluate_f64(rules, &algebra, &cost, NULL));
printf("Minimum cost: %.0f\n", cost);
prices[0] = 1;
check(tididi_evaluate_f64(rules, &algebra, &cost, NULL));
printf("With local storage discounted: %.0f\n", cost);

Output:

Minimum cost: 3
With local storage discounted: 1

11.3. Recognize an impossible choice

Remote storage without encryption violates the rules. Its minimum cost is infinity, so there is no feasible configuration.

const int64_t choice[] = {2,-3};
TididiCircuit *invalid_choice = NULL, *rules_copy = copy(rules), *selected = NULL;
check(tididi_cube(vtree, choice, 2, &invalid_choice, NULL));
check(tididi_and(rules_copy, invalid_choice, &selected, NULL));
check(tididi_evaluate_f64(selected, &algebra, &cost, NULL));
printf("Remote without encryption is feasible: %s\n", isfinite(cost) ? "true" : "false");

Output:

Remote without encryption is feasible: false

11.4. Complete program

Download minimum_cost.c and the shared helper. The source includes cleanup for all handles. Both files are included in the source checkout.