Sorry, I still don't get how it's different from C++, and my point wasn't about `auto` but rather about `std::vector v2`:
std::vector v2 (v1.begin() + 1, v1.begin() + 2);
> However, in the provided example, the Rust type checker can use the provided clue to narrow this down to an exact type
The Rust example is incomplete and its RHS by the time it gets to `.collect()` within the context of `iterator` has to be bound to a particular type of the context via `impl Iterator for <MyContext>`. This is pretty much the same thing as template argument deduction for class templates in C++17 [1][2], and in C++20 it got extended to generic concepts and constraints [3]:
#include <numeric>
#include <vector>
#include <iostream>
#include <concepts>
template <typename T>
requires std::integral<T> || std::floating_point<T>
constexpr auto avg(std::vector<T> const &v) {
auto sum = std::accumulate(v.begin(), v.end(), 0.0);
return sum / v.size();
}
int main() {
std::vector v { 1, 2, 3 };
std::cout << avg(v) << std::endl;
}
Note that nowhere in the snippet do I specify the type explicitly except for the container of type vector.
[1] https://en.cppreference.com/w/cpp/language/template_argument...
[2] https://devblogs.microsoft.com/cppblog/how-to-use-class-temp...
[3] https://www.cppstories.com/2021/concepts-intro/