@@ -234,6 +234,38 @@ fn check_expm1(cx: &LateContext<'_, '_>, expr: &Expr) {
234
234
}
235
235
}
236
236
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
+
237
269
fn check_log_division ( cx : & LateContext < ' _ , ' _ > , expr : & Expr ) {
238
270
let log_methods = [ "log" , "log2" , "log10" , "ln" ] ;
239
271
@@ -250,32 +282,9 @@ fn check_log_division(cx: &LateContext<'_, '_>, expr: &Expr) {
250
282
let left_recv = & left_args[ 0 ] ;
251
283
let right_recv = & right_args[ 0 ] ;
252
284
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 ;
279
288
}
280
289
281
290
// Reduce the expression further for bases 2, 10 and e
@@ -293,7 +302,7 @@ fn check_log_division(cx: &LateContext<'_, '_>, expr: &Expr) {
293
302
cx,
294
303
FLOATING_POINT_IMPROVEMENTS ,
295
304
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) " ,
297
306
"consider using" ,
298
307
suggestion,
299
308
Applicability :: MachineApplicable ,
0 commit comments