What's happening here?

It doesn't matter. As I explained associated has nothing to do with static method or instance method. @jdahlstrom 's explanation is false.
Maybe this helps:

So with self we'd call it an associated method?

The associated only specifies that a certain function (or method) is implemented on the type.

No. I think the description I quoted is explicitly enough: associated functions with a self parameter are called methods.

So what do we call these things on traits that take self? Aren't they methods as well? don't they also deserve love? :smiley:

Yes, they are methods as well :smile:. I'm not saying the opposite :sweat_smile:.

1 Like

Maybe this is the part where the confusion comes from. The reference also mentions the following on associated functions:

When the associated function is declared on a trait, the function can also be called with a path that is a path to the trait appended by the name of the trait. When this happens, it is substituted for <_ as Trait>::function_name.

So, yes, associated functions can also be delcared on traits, but I "reduced the scope" of the conversation when replying to ZiCog to just associated functions for types, to better reflect the intention of jdahlstrom's comment.

Either I'm stupid or this is a direct contradiction to

Associated functions are functions associated with a type.

Maybe they use the term here in the more general sense as not a free function.

Yeah, the reference is imprecise sometimes. As I said, we (the Rust community) even use associated functions as way to refer to associated functions without a self parameter :man_shrugging:.

Maybe once we get a formal specification we will get a more uniform documentation :smiley:.

Yeah, but I think that's okay. It's basically equivalent to what C++ calls a member function I guess. The specialization that such a function that takes self is called a method is a common OO term and unsurprising.

1 Like

I never realised how confusing the naming was until now!
Gonna have a think on what all the names are/should be

Phew, glad it was not just me getting confused.

I no longer think that this is true. Even when using functions declared on a trait, when calling them, be it static or not, their respective implementation is still associated with a type, namely the type the trait is implemented for.
Considering my previous example, also the trait methods called in the free function frobnicate() are associated with the generic type T: Trait and in the concrete invocation are associated with S specifically because of impl Trait for S { ... }. But this really is a terminology hell.

1 Like

The Reference's glossary defines the more general term associated item[1] as:

An associated item is an item that is associated with another item. Associated items are defined in implementations and declared in traits. Only functions, constants, and type aliases can be associated. Contrast to a free item.

Hence, associated functions are those fn items which are nested in an impl or trait block. I think this definition is the most useful and generally-agreed-on one. I would consider ā€œAssociated functions are functions associated with a typeā€ to be most likely simply an error of neglecting to mention traits.


  1. A function definition fn foo() {} is a kind of item. ā†©ļøŽ

1 Like

No, you’re misunderstanding and @ZiCog is right I was talking about associated functions in traits. I’m not sure where you get the idea from that traits don’t have non-self associated functions, they absolutely can and do have. An obvious example is Default.

In Rust, traits can have three types of associated items: consts, types, and functions. If an assoc func takes a self parameter, it’s called a (trait) method.

On the other hand, types can have inherent associated consts and functions (which are, too, called methods if they take a self). Additionally, inherent assoc types are supported on nightly).

And I'm not sure where you get the idea that I said such thing :smile:. I explicitly said that I cornered my arguments to just associated functions for types because the discussion started around traits, and I thought your comment implicitly excluded them.

Another way to think of it all, is in terms of comparison to "regular" OOP:

// regular JS

class Definition {
    static global() {
        return 42;
    }
    method(n) {
        return 16 + n;
    }
}

const is_42 = Definition.global();
const instance = new Definition();
const is_32 = instance.method(16);

Compare this to :

// equivalent in Rust

struct Struct;

impl Struct {
    fn global() -> i32 { 42 }
    fn method(&self, n: i32) -> i32 { 16 + n }
}

let is_42 = Struct::global();
let instance = Struct;
let is_32 = instance.method(16);

Instead of binding any given set of methods to a particular instance of any given class, Rust's compiler binds and resolves them in relation to the type itself. Thus, in your example:

fn something<T: SomeTrait>(thingy: T) {
    // assuming `fn some_method(&self)` is part of a `SomeTrait`
    thingy.some_method();
    // ^ is equivalent to:
    T::some_method(&thingy);
    // this won't compile, though -
    T.some_method() 
    // ^ rustc: expected value, found type parameter `T`
}

In that case should the reference say

Associated functions are functions associated with a type or trait.
?

Sure. Or maybe "Associated functions are functions that are associated items[link to glossary]."

I've seemed to work out what's happening here.

trait SomeTrait {
    fn some_static_method() -> String;
}

struct A;
struct B;

impl SomeTrait for A {
    fn some_static_method() -> String {
        "this is from a".to_owned()
    }
}

impl SomeTrait for B {
    fn some_static_method() -> String {
        "this is from b".to_owned()
    }
}

fn aaa<T: SomeTrait>() {
    println!("{}", T::some_static_method());
}

fn main() {
    aaa::<A>();
    aaa::<B>();
}

Playground link

This code outputs

this is from a
this is from b

Which is cool. It's seemingly calling a method on a type parameter. I never knew one could do this.

2 Likes