[rust-dev] PSA: ~"string" is probably not what you want

Patrick Walton pwalton at mozilla.com
Sun Apr 28 11:14:13 PDT 2013

On 4/28/13 10:57 AM, Lee Braiden wrote:
> Really?  Strings can't just be compared with == ?  To be honest, that
> alone is almost enough to put me off the language -- not only is it ugly
> and unwieldy, but it suggests a lot of limitations in the language's
> memory model / type system / operator overloading, which would also make
> my own code ugly and unwieldy.
> What's the problem with ==, or the difference with equiv(), exactly?

The problem is that `&str` and `~str` are not the same type. We could 
change `Eq` so that it doesn't require the same type on the 
left-hand-side and the right-hand-side, but that would complicate the 
trait system quite a bit.

Currently, overloaded operators do not borrow. I guess we could change 
overloaded operators (or maybe just `==` and `!=`?) to try to borrow the 
left hand side and/or right hand side to make the types match. I think 
this is *probably* OK. However, we need to be careful, because it's 
exactly the kind of thing that could have unforeseen consequences.

"Strings should be comparable with `==` without allocating" is the kind 
of thing that is "obviously true", but trying to do it without thinking 
carefully about the ramifications of borrowing in overloaded operators 
is problematic. We already have quite complex method lookup semantics 
exactly to make things like this just work, and it has fallout when you 
start having to get picky about how many dereferences you do.

To be honest, the tone of your message is a little frustrating, because 
you jumped on one thing that's not ideal (that the different types 
`~str` and `&str` cannot be compared with `==`), said something 
inaccurate (that strings cannot be compared with `==`), and extrapolated 
it to the idea that Rust's type system is "ugly and unwieldy". No, it's 
just that we need to think carefully about how to handle this one case.

 > Is
 > there some way to make it just work, no matter what kind of strings
 > you're comparing?  Perhaps "foo" == (*x) would work, for example?

That doesn't work, because it makes the dynamically sized `str` a type, 
which is incoherent. (It would lead to dynamically sized stack frames, 
or structs or enums with infinite size, and so on.)


More information about the Rust-dev mailing list