I've been working with Rust for a couple years now, and I'm finding that I'm really not having a good time with the borrow checker.

110 points ErisianArchitect

For quite a lot of software, the borrow checker doesn't cause me any problems, but I'm trying to do game development with Rust because I despise using C++, and I'm finding that the weird things that I have to do to get around the borrow checker are just annoying at times.

I'll often find that I have to store things in Option<T> so that I can .take() the value to modify it then .replace() it again when I'm done doing these modifications. This happens when I have one struct that owns the data, but I need mutable access to both the data and the parent struct from some location where these borrow checker rules get in the way. I understand the reason for the borrow checker, but it genuinely makes certain things that could be easy into complete nightmares to implement.

I'm getting to the point where I feel like I'm using Rust for the wrong task, and I don't like that because I really enjoy Rust otherwise. I have no problem making any other type of software, but games are a different beast that require data to be dynamic in a way that is just sometimes infeasible to have a borrow checker for. It's usually not impossible to get around the borrow checker, but it's often inconvenient and introduces other classes of bugs. For example, when I take temporary ownership of data stored in an Option<T> so I can modify it while holding a mutable access to the struct that owns the Option<T>, that data is no longer accessible from within the owner struct, and as such there are other errors that can be introduced.

Call it a skill issue if you'd like. I've been programming for nearly 16 years, 2 of those years in Rust. If there were times when I could just say to the compiler "I know that this operation is safe, just let me modify the data", that would be great.

Really, the problem that I brought up in my example really isn't that big of a problem because I could most likely just use interior mutability if I wanted to, but often times that's an option I don't like very much because then I'm using immutable references rather than mutable ones which makes it so that I can't communicate that the method/function mutates the values through the type system.

The problem I'm facing right now is that I want to embed Lua into my current project, but I'm having a lot of trouble with User Data types. I'm using the mlua crate with the luau-jit flag enabled, and I'm trying to write a Rust type that represents an Vec of arbitrary Lua values, but those Lua values have a lifetime paired with the Lua interpreter, and there's no way to decouple them from the lua interpreter. There's also no way that I've discovered for me to bring the custom user type into the lifetime scope of the lua interpreter. So it seems to me as if there's just no way to create a rust type that's a vec of mlua::Value. It's frustrating me to the point that I want to pull my hair out. I'm considering using rusty_v8 instead because at least Javascript has support for dynamic arrays, so I wouldn't need to plug those types in myself.

Now, you might say "But why don't you just uses tables as arrays?" and my answer to that is: Because it's inefficient.

The other option is to monomorphize all the types that I want to support for the LuaVec and go from there, but then I wouldn't be able to support holding values that have a lifetime, I could only store primitives, which isn't very useful.

If someone smarter than me (I'm not very smart) has any better ideas, I would love to hear them. Tell me I'm a bad programmer all you want, I already know it.