Idea: Properties

There's one case where I wish I had properties-like features in the language: exposing a value publicly, but not allowing modification of this value.

This comes up quite often, because there are plenty of values that aren't some secret implementation detail, but can't be changed without at least checking validity of the value, or upholding some other invariants. For example, Vec.len. It can be read easily and it's always available. But of course it can't be written to without releasing nasal daemons.

So my mini counter-proposal is read-only fields:

struct Vec<T> {
  pub(but only for reading) len: usize
  capacity: usize,
  data: *mut T
}

Pub-read-only fields act as regular fields (read-write) in the same module (where private fields can be accessed), and act as a read-only fields from other places in which they're public.

By read-only I mean you can get & of the field (and copy a Copy value), but you can't get &mut, can't move it, and can't construct a new struct instance with it (for mutation it acts like a private field).

It's better than pub fn get_field(&self) -> &T, because the borrow checker can still track borrow of the individual field, instead of borrowing all of &self.

It's better than just making the field pub, because users of the object can't break invariants of the object.

18 Likes