rust/tests/ui/field_reassign_with_default.rs
Henri Lunnikivi 7b203f3da6 Implement field_reassign_with_default
- Implement `field_reassign_with_default` as a `LateLintPass`
- Avoid triggering `default_trait_access` on a span already linted by
`field_reassigned_with_default`
- Merge `default_trait_access` and `field_reassign_with_default` into
`Default`
- Co-authored-by: Eduardo Broto <ebroto@tutanota.com>
- Fixes #568
2020-10-31 15:49:58 +02:00

110 lines
2.3 KiB
Rust

#![warn(clippy::field_reassign_with_default)]
#[derive(Default)]
struct A {
i: i32,
j: i64,
}
struct B {
i: i32,
j: i64,
}
/// Implements .next() that returns a different number each time.
struct SideEffect(i32);
impl SideEffect {
fn new() -> SideEffect {
SideEffect(0)
}
fn next(&mut self) -> i32 {
self.0 += 1;
self.0
}
}
fn main() {
// wrong, produces first error in stderr
let mut a: A = Default::default();
a.i = 42;
// right
let mut a: A = Default::default();
// right
let a = A {
i: 42,
..Default::default()
};
// right
let mut a: A = Default::default();
if a.i == 0 {
a.j = 12;
}
// right
let mut a: A = Default::default();
let b = 5;
// right
let mut b = 32;
let mut a: A = Default::default();
b = 2;
// right
let b: B = B { i: 42, j: 24 };
// right
let mut b: B = B { i: 42, j: 24 };
b.i = 52;
// right
let mut b = B { i: 15, j: 16 };
let mut a: A = Default::default();
b.i = 2;
// wrong, produces second error in stderr
let mut a: A = Default::default();
a.j = 43;
a.i = 42;
// wrong, produces third error in stderr
let mut a: A = Default::default();
a.i = 42;
a.j = 43;
a.j = 44;
// wrong, produces fourth error in stderr
let mut a = A::default();
a.i = 42;
// wrong, but does not produce an error in stderr, because we can't produce a correct kind of
// suggestion with current implementation
let mut c: (i32, i32) = Default::default();
c.0 = 42;
c.1 = 21;
// wrong, produces the fifth error in stderr
let mut a: A = Default::default();
a.i = Default::default();
// wrong, produces the sixth error in stderr
let mut a: A = Default::default();
a.i = Default::default();
a.j = 45;
// right, because an assignment refers to another field
let mut x = A::default();
x.i = 42;
x.j = 21 + x.i as i64;
// right, we bail out if there's a reassignment to the same variable, since there is a risk of
// side-effects affecting the outcome
let mut x = A::default();
let mut side_effect = SideEffect::new();
x.i = side_effect.next();
x.j = 2;
x.i = side_effect.next();
}