@@ -234,6 +234,38 @@ fn check_expm1(cx: &LateContext<'_, '_>, expr: &Expr) {
234234 }
235235}
236236
237+ // Expressions are considered equivalent if they are constant and evaluate to the
238+ // same value or if they refer to the same variable.
239+ fn are_exprs_equivalent ( cx : & LateContext < ' _ , ' _ > , left : & Expr , right : & Expr ) -> bool {
240+ // Checks whether the values are constant and equal
241+ if_chain ! {
242+ if let Some ( ( left_value, _) ) = constant( cx, cx. tables, left) ;
243+ if let Some ( ( right_value, _) ) = constant( cx, cx. tables, right) ;
244+ if left_value == right_value;
245+ then {
246+ return true ;
247+ }
248+ }
249+
250+ // Checks whether the values are the same variable
251+ if_chain ! {
252+ if let ExprKind :: Path ( ref left_qpath) = left. kind;
253+ if let QPath :: Resolved ( _, ref left_path) = * left_qpath;
254+ if left_path. segments. len( ) == 1 ;
255+ if let def:: Res :: Local ( left_local_id) = qpath_res( cx, left_qpath, left. hir_id) ;
256+ if let ExprKind :: Path ( ref right_qpath) = right. kind;
257+ if let QPath :: Resolved ( _, ref right_path) = * right_qpath;
258+ if right_path. segments. len( ) == 1 ;
259+ if let def:: Res :: Local ( right_local_id) = qpath_res( cx, right_qpath, right. hir_id) ;
260+ if left_local_id == right_local_id;
261+ then {
262+ return true ;
263+ }
264+ }
265+
266+ false
267+ }
268+
237269fn check_log_division ( cx : & LateContext < ' _ , ' _ > , expr : & Expr ) {
238270 let log_methods = [ "log" , "log2" , "log10" , "ln" ] ;
239271
@@ -250,32 +282,9 @@ fn check_log_division(cx: &LateContext<'_, '_>, expr: &Expr) {
250282 let left_recv = & left_args[ 0 ] ;
251283 let right_recv = & right_args[ 0 ] ;
252284
253- if left_method == "log" {
254- if_chain! {
255- // Checks whether the bases are constant and equal
256- if let Some ( ( numerator_base, _) ) = constant( cx, cx. tables, & left_args[ 1 ] ) ;
257- if let Some ( ( denominator_base, _) ) = constant( cx, cx. tables, & right_args[ 1 ] ) ;
258- if numerator_base == denominator_base;
259- then { }
260- else {
261- if_chain! {
262- // Checks whether the bases are the same variable
263- if let ExprKind :: Path ( ref left_base_qpath) = & left_args[ 1 ] . kind;
264- if let QPath :: Resolved ( _, ref left_base_path) = * left_base_qpath;
265- if left_base_path. segments. len( ) == 1 ;
266- if let def:: Res :: Local ( left_local_id) = qpath_res( cx, left_base_qpath, expr. hir_id) ;
267- if let ExprKind :: Path ( ref right_base_qpath) = & right_args[ 1 ] . kind;
268- if let QPath :: Resolved ( _, ref right_base_path) = * right_base_qpath;
269- if right_base_path. segments. len( ) == 1 ;
270- if let def:: Res :: Local ( right_local_id) = qpath_res( cx, right_base_qpath, expr. hir_id) ;
271- if left_local_id == right_local_id;
272- then { }
273- else {
274- return ;
275- }
276- }
277- }
278- }
285+ // Return early when bases are not equal
286+ if left_method == "log" && !are_exprs_equivalent( cx, & left_args[ 1 ] , & right_args[ 1 ] ) {
287+ return ;
279288 }
280289
281290 // Reduce the expression further for bases 2, 10 and e
@@ -293,7 +302,7 @@ fn check_log_division(cx: &LateContext<'_, '_>, expr: &Expr) {
293302 cx,
294303 FLOATING_POINT_IMPROVEMENTS ,
295304 expr. span,
296- "x.log(b) / y.log(b) can be expressed more succinctly " ,
305+ "x.log(b) / y.log(b) can be reduced to x.log(y) " ,
297306 "consider using" ,
298307 suggestion,
299308 Applicability :: MachineApplicable ,
0 commit comments