use selen::prelude::*;
fn main() {
println!("🧩 Table Constraint Demonstrations");
println!("=========================================");
configuration_problem_demo();
println!();
compatibility_matrix_demo();
println!();
lookup_table_demo();
println!();
course_scheduling_demo();
}
fn configuration_problem_demo() {
println!("📋 Example 1: System Configuration Problem");
println!(" Variables: CPU (1=Intel, 2=AMD), GPU (1=NVIDIA, 2=AMD), Motherboard (1=Intel, 2=AMD)");
println!(" Valid combinations enforce compatibility constraints");
let mut m = Model::default();
let cpu = m.int(1, 2); let gpu = m.int(1, 2); let motherboard = m.int(1, 2);
let valid_configs = vec![
vec![int(1), int(1), int(1)], vec![int(1), int(2), int(1)], vec![int(2), int(1), int(2)], vec![int(2), int(2), int(2)], ];
m.table(&[cpu, gpu, motherboard], valid_configs);
if let Ok(solution) = m.solve() {
let cpu_val = match solution[cpu] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let gpu_val = match solution[gpu] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let mb_val = match solution[motherboard] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let cpu_name = if cpu_val == 1 { "Intel" } else { "AMD" };
let gpu_name = if gpu_val == 1 { "NVIDIA" } else { "AMD" };
let mb_name = if mb_val == 1 { "Intel" } else { "AMD" };
println!(" ✅ Valid configuration found:");
println!(" CPU: {} ({})", cpu_val, cpu_name);
println!(" GPU: {} ({})", gpu_val, gpu_name);
println!(" Motherboard: {} socket ({})", mb_val, mb_name);
} else {
println!(" ❌ No valid configuration found");
}
}
fn compatibility_matrix_demo() {
println!("🔗 Example 2: Component Compatibility Matrix");
println!(" Variables: Software (1-3), Hardware (1-3)");
println!(" Table defines which software versions work with which hardware");
let mut m = Model::default();
let software = m.int(1, 3); let hardware = m.int(1, 3);
let compatibility_table = vec![
vec![int(1), int(1)], vec![int(1), int(2)], vec![int(2), int(2)], vec![int(2), int(3)], vec![int(3), int(3)], ];
m.table(&[software, hardware], compatibility_table);
m.new(software.ge(int(2)));
if let Ok(solution) = m.solve() {
let sw_val = match solution[software] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let hw_val = match solution[hardware] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
println!(" ✅ Compatible combination found:");
println!(" Software Version: {}", sw_val);
println!(" Hardware Version: {}", hw_val);
println!(" Status: ✓ Compatible");
} else {
println!(" ❌ No compatible combination found");
}
}
fn lookup_table_demo() {
println!("📊 Example 3: Non-linear Lookup Table");
println!(" Variables: Input (1-5), Output (function values)");
println!(" Table represents a complex function: f(x) = x² - 2x + 3");
let mut m = Model::default();
let input = m.int(1, 5);
let output = m.int(1, 20);
let function_table = vec![
vec![int(1), int(2)], vec![int(2), int(3)], vec![int(3), int(6)], vec![int(4), int(11)], vec![int(5), int(18)], ];
m.table(&[input, output], function_table);
m.new(output.ge(int(5)));
m.new(output.le(int(12)));
if let Ok(solution) = m.solve() {
let in_val = match solution[input] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let out_val = match solution[output] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
println!(" ✅ Function evaluation found:");
println!(" Input: {}", in_val);
println!(" Output: f({}) = {}", in_val, out_val);
println!(" Verification: {}² - 2×{} + 3 = {}", in_val, in_val, in_val*in_val - 2*in_val + 3);
} else {
println!(" ❌ No solution found");
}
}
fn course_scheduling_demo() {
println!("📚 Example 4: Course Scheduling Problem");
println!(" Variables: Course (1-3), Time slot (1-4), Room (1-2)");
println!(" Table defines valid (course, time, room) combinations");
let mut m = Model::default();
let course = m.int(1, 3); let time_slot = m.int(1, 4); let room = m.int(1, 2);
let schedule_table = vec![
vec![int(1), int(1), int(2)], vec![int(1), int(2), int(2)], vec![int(1), int(3), int(2)], vec![int(1), int(4), int(2)],
vec![int(2), int(3), int(1)], vec![int(2), int(4), int(1)],
vec![int(3), int(1), int(1)], vec![int(3), int(2), int(1)], vec![int(3), int(4), int(1)], ];
m.table(&[course, time_slot, room], schedule_table);
m.new(time_slot.le(int(2)));
if let Ok(solution) = m.solve() {
let course_val = match solution[course] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let time_val = match solution[time_slot] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let room_val = match solution[room] {
Val::ValI(i) => i,
Val::ValF(f) => f as i32,
};
let course_name = match course_val {
1 => "Math",
2 => "Physics",
3 => "Chemistry",
_ => "Unknown"
};
let time_name = match time_val {
1 => "9:00 AM",
2 => "11:00 AM",
3 => "1:00 PM",
4 => "3:00 PM",
_ => "Unknown"
};
let room_name = if room_val == 1 { "Lab" } else { "Classroom" };
println!(" ✅ Schedule found:");
println!(" Course: {} ({})", course_val, course_name);
println!(" Time: {} ({})", time_val, time_name);
println!(" Room: {} ({})", room_val, room_name);
} else {
println!(" ❌ No valid schedule found");
}
}