Skip to content

Commit 5b1b65b

Browse files
committed
Auto merge of #7639 - Jarcho:whitelist_cheap_functions, r=camsteffen
Improve heuristic for eagerness suggestion Still to be done: * a more complete list of cheap functions * a way to limit the complexity of cheap expressions changelog: Improve heuristics for `or_fun_call` and `unnecessary_lazy_evaluations`
2 parents 0def42f + 2938ffd commit 5b1b65b

17 files changed

+408
-240
lines changed

clippy_lints/src/functions/too_many_lines.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,8 +56,8 @@ pub(super) fn check_fn(
5656
continue;
5757
}
5858
} else {
59-
let multi_idx = line.find("/*").unwrap_or_else(|| line.len());
60-
let single_idx = line.find("//").unwrap_or_else(|| line.len());
59+
let multi_idx = line.find("/*").unwrap_or(line.len());
60+
let single_idx = line.find("//").unwrap_or(line.len());
6161
code_in_line |= multi_idx > 0 && single_idx > 0;
6262
// Implies multi_idx is below line.len()
6363
if multi_idx < single_idx {

clippy_lints/src/methods/from_iter_instead_of_collect.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ fn extract_turbofish(cx: &LateContext<'_>, expr: &hir::Expr<'_>, ty: Ty<'tcx>) -
6969
// i.e.: 2 wildcards in `std::collections::BTreeMap<&i32, &char>`
7070
let ty_str = ty.to_string();
7171
let start = ty_str.find('<').unwrap_or(0);
72-
let end = ty_str.find('>').unwrap_or_else(|| ty_str.len());
72+
let end = ty_str.find('>').unwrap_or(ty_str.len());
7373
let nb_wildcard = ty_str[start..end].split(',').count();
7474
let wildcards = format!("_{}", ", _".repeat(nb_wildcard - 1));
7575
format!("{}<{}>", elements.join("::"), wildcards)

clippy_lints/src/methods/or_fun_call.rs

Lines changed: 22 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,12 @@
11
use clippy_utils::diagnostics::span_lint_and_sugg;
2-
use clippy_utils::eager_or_lazy::is_lazyness_candidate;
3-
use clippy_utils::is_trait_item;
2+
use clippy_utils::eager_or_lazy::switch_to_lazy_eval;
43
use clippy_utils::source::{snippet, snippet_with_applicability, snippet_with_macro_callsite};
5-
use clippy_utils::ty::implements_trait;
6-
use clippy_utils::ty::{is_type_diagnostic_item, match_type};
7-
use clippy_utils::{contains_return, last_path_segment, paths};
4+
use clippy_utils::ty::{implements_trait, match_type};
5+
use clippy_utils::{contains_return, is_trait_item, last_path_segment, paths};
86
use if_chain::if_chain;
97
use rustc_errors::Applicability;
108
use rustc_hir as hir;
11-
use rustc_hir::{BlockCheckMode, UnsafeSource};
129
use rustc_lint::LateContext;
13-
use rustc_middle::ty;
1410
use rustc_span::source_map::Span;
1511
use rustc_span::symbol::{kw, sym};
1612
use std::borrow::Cow;
@@ -96,25 +92,10 @@ pub(super) fn check<'tcx>(
9692
(&paths::RESULT, true, &["or", "unwrap_or"], "else"),
9793
];
9894

99-
if let hir::ExprKind::MethodCall(path, _, [self_arg, ..], _) = &arg.kind {
100-
if path.ident.name == sym::len {
101-
let ty = cx.typeck_results().expr_ty(self_arg).peel_refs();
102-
103-
match ty.kind() {
104-
ty::Slice(_) | ty::Array(_, _) | ty::Str => return,
105-
_ => (),
106-
}
107-
108-
if is_type_diagnostic_item(cx, ty, sym::Vec) {
109-
return;
110-
}
111-
}
112-
}
113-
11495
if_chain! {
11596
if KNOW_TYPES.iter().any(|k| k.2.contains(&name));
11697

117-
if is_lazyness_candidate(cx, arg);
98+
if switch_to_lazy_eval(cx, arg);
11899
if !contains_return(arg);
119100

120101
let self_ty = cx.typeck_results().expr_ty(self_expr);
@@ -166,26 +147,30 @@ pub(super) fn check<'tcx>(
166147
}
167148
}
168149

169-
if args.len() == 2 {
170-
match args[1].kind {
150+
if let [self_arg, arg] = args {
151+
let inner_arg = if let hir::ExprKind::Block(
152+
hir::Block {
153+
stmts: [],
154+
expr: Some(expr),
155+
..
156+
},
157+
_,
158+
) = arg.kind
159+
{
160+
expr
161+
} else {
162+
arg
163+
};
164+
match inner_arg.kind {
171165
hir::ExprKind::Call(fun, or_args) => {
172166
let or_has_args = !or_args.is_empty();
173-
if !check_unwrap_or_default(cx, name, fun, &args[0], &args[1], or_has_args, expr.span) {
167+
if !check_unwrap_or_default(cx, name, fun, self_arg, arg, or_has_args, expr.span) {
174168
let fun_span = if or_has_args { None } else { Some(fun.span) };
175-
check_general_case(cx, name, method_span, &args[0], &args[1], expr.span, fun_span);
169+
check_general_case(cx, name, method_span, self_arg, arg, expr.span, fun_span);
176170
}
177171
},
178172
hir::ExprKind::Index(..) | hir::ExprKind::MethodCall(..) => {
179-
check_general_case(cx, name, method_span, &args[0], &args[1], expr.span, None);
180-
},
181-
hir::ExprKind::Block(block, _)
182-
if block.rules == BlockCheckMode::UnsafeBlock(UnsafeSource::UserProvided) =>
183-
{
184-
if let Some(block_expr) = block.expr {
185-
if let hir::ExprKind::MethodCall(..) = block_expr.kind {
186-
check_general_case(cx, name, method_span, &args[0], &args[1], expr.span, None);
187-
}
188-
}
173+
check_general_case(cx, name, method_span, self_arg, arg, expr.span, None);
189174
},
190175
_ => (),
191176
}

clippy_lints/src/methods/unnecessary_lazy_eval.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ pub(super) fn check<'tcx>(
3030
return;
3131
}
3232

33-
if eager_or_lazy::is_eagerness_candidate(cx, body_expr) {
33+
if eager_or_lazy::switch_to_eager_eval(cx, body_expr) {
3434
let msg = if is_option {
3535
"unnecessary closure used to substitute value for `Option::None`"
3636
} else {

clippy_lints/src/option_if_let_else.rs

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -147,11 +147,7 @@ fn detect_option_if_let_else<'tcx>(cx: &LateContext<'tcx>, expr: &Expr<'tcx>) ->
147147
let capture_mut = if bind_annotation == &BindingAnnotation::Mutable { "mut " } else { "" };
148148
let some_body = extract_body_from_expr(if_then)?;
149149
let none_body = extract_body_from_expr(if_else)?;
150-
let method_sugg = if eager_or_lazy::is_eagerness_candidate(cx, none_body) {
151-
"map_or"
152-
} else {
153-
"map_or_else"
154-
};
150+
let method_sugg = if eager_or_lazy::switch_to_eager_eval(cx, none_body) { "map_or" } else { "map_or_else" };
155151
let capture_name = id.name.to_ident_string();
156152
let (as_ref, as_mut) = match &let_expr.kind {
157153
ExprKind::AddrOf(_, Mutability::Not, _) => (true, false),

0 commit comments

Comments
 (0)