#Iterating over ArrayList makes captured value const

1 messages · Page 1 of 1 (latest)

mental briar
#

This gives me the compiler error that I cannot assign to const

const Value = struct {
  x: u8
};

pub fn main() !void {
  var list = std.arrayList(Value).init(allocator);
  try list.append(.{.x = 1});
  try list.append(.{.x = 2});
  try list.append(.{.x = 3});

  for (list.items) |item| {
    item.x += 1;
  }
}

If I iterate over the indices of the list like this, it works fine. But is there a better way of iterating over the items of the list as var instead of const?

const Value = struct {
  x: u8
};

pub fn main() !void {
  var list = std.arrayList(Value).init(allocator);
  try list.append(.{.x = 1});
  try list.append(.{.x = 2});
  try list.append(.{.x = 3});

  for (0..list.items.len) |i| {
    list.items[i].x += 1;
  }
}
solid ermine
#

capture by reference

#

for (list.items) |*item|

mental briar
#

item is now a pointer and this makes it mutable?

solid ermine
#

well it's a mutable pointer but the variable itself is still const

#

captures are always const

#

like you can't do item = some_other_pointer;

#

but being a mutable pointer lets you change the item that it refers to, the one inside the arraylist, which is what you wanted

mental briar
#

ah ok, it is a const pointer but it doesnt point to a const value and therefore I can mutate it

umbral lotus
#

since list.items is mutable, it'll be a pointer-to-mutable as well yeah

#

if the array/slice you're iterating over is mutable, then the pointer capture will *T, so you can modify the underlying data. If the array/slice is immutable it'll be *const T

mental briar
#

I thought if I make the list const const list = ... I cant assign a new list to the variable, and not that the elements in the list are mutable

solid ermine
#

well a const arraylist would still contain a mutable slice i think, cuz that's how the type is defined

#

but you wouldn't be able to call methods on the arraylist that take a mutable self pointer, like append

mental briar
#

yeah true

umbral lotus
#

the bytes of the arraylist object (slice ptr/len & capacity) are immutable but slice contents are still mutable so list.items is mutable