(&mut self, a: Val, b: Val)
| 477 | } |
| 478 | |
| 479 | pub fn sub_vals(&mut self, a: Val, b: Val) -> Result<Val, VmErr> { |
| 480 | if a.is_int() && b.is_int() |
| 481 | && let Some(r) = a.as_int().checked_sub(b.as_int()) |
| 482 | && (Val::INT_MIN..=Val::INT_MAX).contains(&r) { |
| 483 | return Ok(Val::int(r)); |
| 484 | } |
| 485 | if let Some((af, bf)) = coerce_floats(a, b, &self.heap) { return Ok(Val::float(af - bf)); } |
| 486 | if let (Some(ai), Some(bi)) = (as_i128(a, &self.heap), as_i128(b, &self.heap)) { |
| 487 | return self.int_to_val(ai.checked_sub(bi)); |
| 488 | } |
| 489 | // Set / frozenset difference: fresh set of `a` elements not in `b`. |
| 490 | if let (Some(sa), Some(sb)) = (self.clone_set_items(a), self.clone_set_items(b)) { |
| 491 | let items: Vec<Val> = sa.iter().filter(|&&v| !sb.contains(v, &self.heap)).copied().collect(); |
| 492 | let frozen = matches!(self.heap.get(a), HeapObj::FrozenSet(_)); |
| 493 | return self.alloc_set_result(items, frozen); |
| 494 | } |
| 495 | Err(VmErr::TypeMsg(s!("unsupported operand type(s) for -: '", str self.type_name(a), "' and '", str self.type_name(b), "'"))) |
| 496 | } |
| 497 | |
| 498 | pub fn mul_vals(&mut self, a: Val, b: Val) -> Result<Val, VmErr> { |
| 499 | if a.is_int() && b.is_int() |
no test coverage detected