I would say that for a "usual application" you should peek either a sane dynamic language (Python, Ruby, Clojure? They are all good), or a sane statically typed language with garbage collection.
Manually managing memory is just a significant mental and API overhead (even if the compiler controls that you do it right). So Rust should not be a good choice for such tasks.
The caveat here is that I don't know any sane statically typed language with garbage collection (I haven't tried Go or Swift though. OCaml comes close as a language, but incredibly far as a platform).
So given that Rust is incredibly sane and pragmatic language, and despite the lack of GC and a established libraries/frameworks network, Rust may be a meaningful choice for tasks, where you would usually go with, say, Java.
In Racket development systems ( https://racket-lang.org/ , a Scheme) you use several different languages (regular, typed Racket, simplified, etc). Perhaps a Rust-variant language could be invented, that shares several characteristics of Rust (and interfaces in a simple way with Rust), and is simpler to use where performance isn't the most important concern (where you may want to use an OCaML or F#).
I'm surprised so many people are suggesting not Rust.
Right now Rust can feel too painful to use for "simple" cases, but that won't always be the case. The things that are most frustrating now will not exist forever.
Even now there are different styles to program Rust in to make your life easier or harder. For example, if you put things on the heap and clone a lot Rust is much easier to write than if you avoid allocations.
Rust is a new kind of language, and it sets all the design knobs in a particular way so some things are easy and some things are hard. I'm hopeful that Rust could someday be used as a transpilation target for other Rust-like languages that set the knobs differently. For example you could have one that makes everything Gc<Any> by default, or that prefers dynamic dispatch to static.
It is. A single type that combines the two would help a lot I think.
Maybe it would be a good idea to have a marker trait for automatic cloning (like Copy but without the implication that cloning is just copying bits). Then you could create types wrapping Rc so that you wouldn't have to think about memory when you use them, like for primitive types.
I agree, when not trying to think too much about memory, I've found Rust doesn't get in the way when you understand the language semantics, and its type system is perfectly capable of capturing business logic, again when you understand the language semantics.
So it's totally possible to write programs with a focus on business logic over memory. And a few things I find really refreshing coming from C# is that not everything is mutable to anybody, and errors don't leak all over the shop.
I think Rust's type system makes it great for writing large applications, regardless of performance questions. It helps you structure your code cleanly by explicitly tracking read/write access to state at different points in the code and makes it easy to confidently refactor code. The memory model is a challenge to learn, but once you've learned it I don't think its a problem.
I also don't find the type system to be a problem for exploratory programming.
I have been using Rust for almost a year now and I have to admit that I do not use Python that much anymore since, so I might be a little bit biased by the fact that Rust is my every-day language.
This semester I have a couple of school assignments to do in Python (e.g. implementing a basic tcp / udp chat) and when coding in Python I realize I am spending a lot of time debugging my programs. Compared to Rust, in Python it's easy to miss some corner cases or exceptions that only pop up at run time when conditions x, y and z are met.
In Rust everything is explicit, it's a lot easier to reason about. When the code compiles there is a good chance that it does what you want it to. Errors are well explained and often trivial to correct. I have also become dependent on all the niceties the Rust compiler gives us, like warning for unused code. When prototyping you tend to refactor a lot, warnings like that are invaluable to see at a glance what code can safely be removed.
It's true, writing Rust is more verbose and takes longer. But in the long run, when you sum everything up: Coding + Debugging + Refactoring I am pretty sure I am more productive in Rust, even for relatively small projects.
I'm brand new to rust, just started the tutorials a couple of days ago. So my opinion may not have much value. But I've got 40+ years of professional software development experience, most of the most recent 20 years in Java. I'm looking at rust, D, and go for application development. Its clear to me that normal application development is not the sweet spot for the rust designers. OK, I can live with that. But I disagree that I should be happy with existing application languages like Java, Python, Ruby, etc. Maybe I'm old and biased, but I much prefer strongly typed languages. I've done years of professional development with smalltalk, which nearly has no types.
Modern computers have lots of cores. Smartphones have 4, desktops have 8 or 16. Writing multi-threaded applications in something like Java is infeasible. Sure, wizards can do it, but you can't hire ten wizards for your application without Google-level money.
So my dream, in addition to a pony, is a language that can allow normal professional programmers to write correct code. At this point in my learning/evaluation, rust looks like the best. I might change my mind as I get more experience, get smarter, better looking, and wiser.
I am a retired software developer and manager with a lot of years of experience writing code in more languages than I can remember. I've taken a hard look at Rust and I don't think it's appropriate for situations where ultimate performance isn't necessary. Systems that provide garbage collection are much easier to use. In Rust, you are doing memory management manually, as you do in C, but Rust insures that you do it correctly, which C does not. Garbage collection removes memory management from the programmer's set of responsibilities. As someone who has written a lot of Lisp and Scheme code over the years, I must say that I am a convert to statically typed languages, especially since I learned Haskell. The GHC compiler is a work of art and once you make that thing happy, you are very close to having a bug-free program, modulo algorithmic/logic errors. I think Haskell is an excellent choice for "high-level" situations. It takes some doing to learn it, but it's worth it, and it's supported by an excellent set of libraries, both official and contributed. And very important -- well-written Haskell code is very readable (one of Python's virtues and a huge problem with other scripting languages like tcl or perl; Rust is not great in that regard, either, in my opinion).
To me, the thing that is making Rust so compelling, even for applications where the lower-level memory management are making it a bit more work, is how Rust/cargo have dealt so nicely with so many important aspects of software development.
Crates/modules. This is invaluable for programming in the large. It allows software developed independently without having to worry about the packages stepping on each other. The closest I've seen to this is the SML basis system.
Real generics. This seems more common in other languages (except Go).
Cargo has spoiled me to pretty much everything else. The good news, is that I think it is influencing people. Haskell with cabal sandboxes gets close. I think I pull out more hair each time I see a wiki say: "sudo pip ...".
I am finding, however, that the memory management overhead in Rust, is more an issue of learning how to think that way. I guess mostly lacking is just libraries, which isn't surprising given how young Rust is.
I think I also use Rust more for things that are not specially "low-level". I tend to sometimes have an "attack of the .clone()s" attitude to memory problems :D, though it isn't always the best way to appease the borrow checker.
I guess having a garbage collector would be a way to solve cases which are not performance critical, but it doesn't solve all issues (e.g. concurrency). I think I'd prefer some good libraries for persistent data structures, allowing to program in a more functional idiom without worrying about the borrow checker (once everything is immutable and reference counted, the borrow checker should not be a problem).
This is something I hear a lot and I just don't think its true. Rust's memory model requires you to think explicitly about scope and state, two things that are very important to writing understandable code. So while Rust's memory model is an effective strategy for writing safe code without garbage collection, its also an effective strategy for writing extensible, maintainable programs. That they are also fast might just be a free benefit for some users.
Of course, later in your post, you say you are very excited by Haskell. Haskell's requirements about purity solve essentially the same problem I've just described, and like the Rust memory model, these aspects of Haskell have a very high overhead to learning. I think this is a significant similarity between Rust and Haskell, more than their actual language similarities - that they have features which have a tough learning curve but which prevent programs from becoming balls of mud.
I actually don't like the idea of .clone() or .clone() by default.
That is what makes Rust even more beautiful, being efficient by using references where appropriate and not worrying about safety. In other languages when it gets hard to track references(pointers), you throw GC or smart pointers at the problem, while in Rust this is not necessary in most cases.
At my job we work with a big C++ codebase and to solve this problem, people have just created a reference counted pointers nightmare just to keep the application a float