It makes sense that you don't see the value of Rust if you spend most of your time developing solo.
The value of these checks is not just to reduce bugs in production code. It's nice that that happens, but that's not even the primary value of the borrow checker. The primary value is that having these checks (lifetimes, bounds checks, -- everything that makes Rust annoying to write) makes refactoring on a shared codebase significantly easier. This means that you are not introducing bugs in a refactor, so you can refactor faster, which means you can ditch bad architectures sooner, which compounds and saves enormous amounts of developer time and $$. And it's a knock-on effect that increases in value as the team grows larger.
Keeping track of lifetimes and bounds for a solo dev is quite easy as you say. Keeping track of lifetimes and bounds for the other dozen devs on my team? In all external dependencies? Extremely difficult. Impossible in a large codebase, actually, given the number of mem safety bugs that appear even in mature C codebases. It's collaboration that is the source of these bugs, that these checks work to mitigate.
I sort of wondered why C did not have a package management system, until I started working on a large C codebase. There is a reason Rust has cargo and C does not; it has nothing to do with whether or not someone decided to write cargo and everything to do with Rust's language features.
That's a different and refreshing perspective to look from, thanks.
I'm aware that my view is somewhat biased because I'm a solo dev which works on small to large projects by myself, and things get exponentially harder as more people mangle the same code base. That's very true.
What I was trying to highlight is basically neither C or C++ are "free for all without recourse". Esp. C++ has many features, but they're opt-in, where in Rust they're opt-out.
Also many newer developers don't understand that compilation used to take way longer on olden times even with simpler languages and compilers. Hence, the thing Rust doing today was "impossible" in the older days.
For the last time, I think Rust is a nice language, and I won't be annoyed by its limitations. What bothers me with no end is vilifying other languages and pushing rust as a silver bullet and savior. Other than that, Rust is just another tool which works for some things very well, and not very well for others.
The value of these checks is not just to reduce bugs in production code. It's nice that that happens, but that's not even the primary value of the borrow checker. The primary value is that having these checks (lifetimes, bounds checks, -- everything that makes Rust annoying to write) makes refactoring on a shared codebase significantly easier. This means that you are not introducing bugs in a refactor, so you can refactor faster, which means you can ditch bad architectures sooner, which compounds and saves enormous amounts of developer time and $$. And it's a knock-on effect that increases in value as the team grows larger.
Keeping track of lifetimes and bounds for a solo dev is quite easy as you say. Keeping track of lifetimes and bounds for the other dozen devs on my team? In all external dependencies? Extremely difficult. Impossible in a large codebase, actually, given the number of mem safety bugs that appear even in mature C codebases. It's collaboration that is the source of these bugs, that these checks work to mitigate.
I sort of wondered why C did not have a package management system, until I started working on a large C codebase. There is a reason Rust has cargo and C does not; it has nothing to do with whether or not someone decided to write cargo and everything to do with Rust's language features.