Pular para o conteúdo

Ciclo de vida e memória

Construção, teardown, referências fracas e o coletor: o que acontece com um objeto do spawn ao descarte.

Do spawn ao descarte#

  1. on_spawn da metaclasse — pode entregar um objeto pronto;
  2. __new__ — idem;
  3. os padrões dos campos, copiados quando mutáveis;
  4. os parâmetros do cabeçalho, com tipo e padrão;
  5. setup (ou initiate, ou __init__), e o corpo solto do blueprint;
  6. as invariantes e on_ready;
  7. …a vida do objeto…
  8. teardown (ou __del__) quando o último nome o solta.

teardown#

O DataForge roda sobre o CPython e herda o modelo de memória dele: cada objeto tem um contador de referências e morre no instante em que ele chega a zero. É por isso que teardown roda na hora, e não "em algum momento". Só os blueprints que declaram finalizador pagam por ele.

dataforge
log := []

blueprint Arquivo(nome):
    action teardown():
        log.append($"fechou {self.nome}")

a := spawn Arquivo("dados.csv")
a := void
assert log is ["fechou dados.csv"]

Referências fracas#

Uma referência fraca aponta sem segurar. É o que um cache e um registro de observadores precisam — guardar o objeto enquanto ele existir, sem ser a razão de ele existir. Um cache com referência forte é o vazamento de memória mais comum que existe.

dataforge
adopt Arcane.Memoria as Mem

blueprint Sessao:
    usuario := "ana"

s := spawn Sessao()
ref := Mem.fraca(s)
assert ref.viva()
assert ref.obter().usuario is "ana"

s := void
assert not ref.viva()
assert ref.obter() is void

cache := Mem.mapa_fraco()
chave := spawn Sessao()
cache.definir(chave, "dados caros")
assert cache.tamanho is 1
chave := void
assert cache.tamanho is 0

O coletor#

FunçãoO que responde
Mem.coletar()força a coleta de ciclos; devolve quantos objetos soltou
Mem.vivos(Tipo)quantas instâncias do blueprint (e das filhas) existem agora
Mem.tamanho(obj)bytes aproximados do objeto e do que só ele alcança
Mem.referencias(obj)o contador do CPython
Mem.ao_descartar(obj, acao)roda a ação quando o objeto for coletado
Mem.estatisticas()gerações, limiares e coletas

Para economizar memória por objeto, slots guarda os campos numa lista em vez de num vault — ver slots.