Testing for not None and panicking

What's the ideomatic way to do this?

let result = somehash.insert(newitem);
match result { 
    Ok(dup) => panic!("Dupilcate entry inserted into hash"),
    None =>()
}

Is there something short like unwrap() for that situation? Thanks, and happy holidays.

You can write:

assert!(somehash.insert(newitem).is_none(), "duplicate entry")
2 Likes

If you're open to using a feature, here's a 1-liner (use expect_none):

".expect_none()" looks good. There is, however, ongoing discussion over whether to keep it.

The trouble with

assert!(somehash.insert(newitem).is_none(), "duplicate entry")

is that it's bad form to write an assert with needed side effects. Some level of optimization might disable asserts.

3 Likes

This is not true for the assert! macro in Rust (or its friend assert_eq! or assert_ne!), which is always executed regardless of optimization level.

In Rust, debug_assert! (or its friend debug_assert_eq! or debug_assert_ne!) is used for optional assertions that can be disabled in release builds.

(Note that the C/C++ assert macro is equivalent to the Rust debug_assert! macro, not the Rust assert! macro..)

17 Likes

Except for when the compiler "proves", that the assertion can never fail; then it's fine to remove the assertion from the compiler-site.

1 Like

Importantly, the compiler would also have to prove that the assertion has no other side-effects. So yes, the optimizer is always free to remove any code that is guaranteed to have no effect, but that's true whether it's an assertion or not.

Again, this is unlike the C assert macro, which is typically stripped completely in release builds, even if this changes program behavior. The Rust assert! macro has the same semantics in debug and release builds.

9 Likes

assert!() is guaranteed not to be removed to the point where it's often used for ensuring preconditions to unsafe code, even in the standard library. You absolutely can rely on it.

5 Likes

What's the type of somehash? If it's a HashMap, then theinsert takes a key and a value, if it's a HashSet, then it should return just a bool. Assuming a HashMap, surely this is too much, but I feel I would use the entry API:

match somehash.entry(key) {
    Entry::VacantEntry(entry) => entry.insert(value),
    Entry::OccupiedEntry(_} => panic!("duplicate...")
}

Also I feel I would probably return an error rather than panic in this case, but I don't know your full use case

2 Likes

Usually I would, but here I have some vectors and hashes which have to remain in sync. I'm transferring ownership of a subtree from one tree to another. If the tests passed which allow that to start, it has to finish cleanly or the data structure is broken.

1 Like

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.