-
Notifications
You must be signed in to change notification settings - Fork 15.2k
Description
| Bugzilla Link | 44556 |
| Resolution | FIXED |
| Resolved on | Jan 23, 2020 14:03 |
| Version | trunk |
| OS | All |
| Blocks | #43900 |
| CC | @zmodem,@mordante,@LebedevRI,@zygoloid,@Weverything |
| Fixed by commit(s) | 41fcd17 |
Extended Description
The warning -Wrange-loop-analysis diagnoses two issues:
- When the return value of the iterator's operator* is a reference type, but it is captured by value: this means we've made an unnecessary copy.
- When the return value of the iterator's operator* is not a reference type, but is captured by reference: this is fine, but suggests there is no copy when in fact there is one. (Well, because of RVO there might actually be no copy.)
Unfortunately the warning flips in template code:
struct Rng {
struct iterator {
int operator*() const;
iterator& operator++();
bool operator!=(const iterator&) const;
};
iterator begin() const;
iterator end() const;
};
struct X {
X() = default;
X(const X&);
};
template
void f(const T& t) {
// Variant 1.
for (const auto& _ : t) // Warning from (1).
;
// Variant 2.
for (const auto _ : t) // Warning from (2).
;
}
void g()
{
X array[3];
f(array); // (1)
f(Rng{}); // (2)
}
This means however I write f, there will always be a warning, although the first variant is actually correct. I think that we should either not warn about the second issue, or drop the warning when template-dependent types are involved. However, we should in my opinion always warn about the first issue.