# Structs & methods

A `struct` defines data; an `impl` block defines the functions and methods that operate on it.

```cplus
struct Point {
    x: i32,
    y: i32,
}

impl Point {
    // Associated function — no receiver. Called via `Point::new(...)`.
    fn new(x: i32, y: i32) -> Point {
        return Point { x: x, y: y };
    }

    // Instance method — receiver is `self`. Called via `p.translate(...)`.
    fn translate(mut self, dx: i32, dy: i32) {
        self.x = self.x +% dx;
        self.y = self.y +% dy;
    }

    fn magnitude_squared(self) -> i32 {
        return self.x *% self.x +% self.y *% self.y;
    }
}

fn main() -> i32 {
    let mut p: Point = Point::new(1, 2);
    p.translate(3, 4);
    return p.magnitude_squared();
}
```

Note the strict separation: `::` reaches a type's associated items (`Point::new`), and `.` reaches an instance's methods (`p.translate`).

## Struct literals

```cplus
let x: i32 = 1;
let y: i32 = 2;
let p: Point = Point { x: x, y: y };
```

There is no field shorthand today; write every `name: value` pair explicitly.

## Field visibility

Fields are module-private by default. `pub` is the export marker, so a public field is always intentional:

```cplus
struct Public {
    pub value: i32,                     // visible to other modules
    internal: i32,                      // module-private
}
```

## The three receiver forms

Methods take one of three receivers, which mirror the parameter markers:

```cplus
impl Buf {
    fn read(self) { ... }                   // shared borrow (by-value on a Copy type)
    fn write(mut self) { ... }              // exclusive borrow, may mutate
    fn into_raw(move self) -> *u8 { ... }   // consumes self
}
```

Bare `self` is the shared, read-only borrow; `mut self` may mutate and the change propagates back to the caller; `move self` consumes the receiver. The full model, including why a bare `self` reads but a bare parameter moves, is in [Ownership](/docs/ownership).
