Make clippy suggest more generic code

It may not be such a great idea, but I imagine that it could occasionally be useful if clippy had a lint for code that could potentially be made generic. Say we have some code like:

fn print(x: &str) {
   println!("{}", x);
}

Cargo clippy could lint something like:

warning: potential use of generic code.
   --> src/main.rs:3:0
    |
3   |         fn print(x: &str) {
    |             ^ help: try changing `&str` to `impl Display`
    |
    = note: `#[warn(generalizable_code)]` is on 

warning: 1 warning emitted

I imagine that it shouldn't be so hard to implement.

Drawbacks

Some drawbacks are obvious, like what if that function was named print_str, or if the input variable is named string. Function and variable names that imply any given type may not play well with the suggestion.

Also, some code may be generalizable but the generic form may be too verbose or complicated to be helpful. In that case suggestions could be filtered by length. I also fear that almost all functions in a crate may be linted, as traits are used so often instead of ordinary methods.

Either way, I believe it could be useful at times as an optional lint, and as far as I know something like this doesn't currently exist.

2 Likes

I think it's an interesting idea, feel free to create an issue in the Clippy repo for this lint (link). We usually track new suggestions for Clippy lints there.

This lint would most likely fit in the of the pedantic group :upside_down_face:

2 Likes

Generic version is not always better. There's a cost in compilation time (the function can't be pre-compiled in a dependency, it gets re-compiled when it's used) and code bloat (you'll end up with a separate copies for &str, &String, String, etc).

For example, Rust's standard library intentionally does the opposite of this!

fn path_related_function<P: AsRef<Path>>(path: P) {
    _path_related_function(path.as_ref());
}

fn _path_related_function(path: &Path) { actual code here }
6 Likes

Although I believe there was some (unfinished?) work that would have made the compiler s after such that that oddity is no longer necessary.

It would be interesting if rust-analyzer could have an action that did the transformation.

I created the issue here. There are a lot of tradeoffs with this idea but I think it could be very helpful to have something like this available.

2 Likes

Is this approach also useful for methods, or only fns?

I'm asking because I can see that going either way.

Methods and functions are the same thing internally. Just a bit of sugar.

And llogic went so far as to write a crate to do this for you: Momo ยท Get Back Some Compile Time From Monomorphization โ€” Llogiq on stuff

2 Likes

I expect restricted would be the better category.

2 Likes