Is your feature request related to a problem? Please describe.
Array::clear() makes an array logically empty, but on non-JavaScript backends it intentionally retains the backing buffer and the references stored in its slots. This is useful when the capacity will be reused, but it is unsuitable when those references must be severed explicitly to break a cycle.
One motivating case is a coroutine or scheduler state that owns an array-backed queue of callbacks/closures. The queued callbacks may capture the coroutine state, producing a cycle like:
coroutine state -> callback queue -> callback closure -> coroutine state
When the coroutine is completely finished, emptying and detaching the queue can break this cycle and make the objects eligible for reclamation.
Array::release_unused(placeholder=...) can overwrite the retained slots after clear(), but it requires a value of T. For callback/function types and other reference-bearing types, there may be no canonical harmless default value. It also fills the entire unused capacity and retains the allocation.
Describe the solution you'd like
Add an operation that empties an array and detaches its backing storage without requiring a placeholder. Tentatively, this could be named Array::reset:
pub fn[T] Array::reset(self : Array[T]) -> Unit {
self.len = 0
self.buf = []
}
The intended contract is:
length() is zero afterwards.
- The backing storage is relinquished (
capacity() becomes zero where capacity is meaningful).
- References held by both the live prefix and unused capacity are no longer reachable through the array, allowing cycles to be broken.
- No
T, Default bound, or placeholder is required.
- The array remains valid and can be reused by pushing new elements.
- The API is available consistently across backends; on JavaScript, truncating the underlying array to length zero is sufficient.
Replacing the buffer directly also avoids explicitly overwriting every retained slot as release_unused does. Actual reclamation remains runtime-dependent, and an outstanding ArrayView may keep the previous buffer reachable subject to the existing view-lifetime rules.
The name is open for discussion. Since reset on some existing buffer-like types means “become empty while retaining capacity,” a more explicit name such as clear_and_release or clear_and_shrink may communicate the storage behavior better.
Describe alternatives you've considered
array.clear(); array.release_unused(placeholder=...) breaks references but requires a suitable placeholder, scans the unused capacity, and retains the allocation.
array.clear(); array.shrink_to_fit() is semantically close and does not need a placeholder. A dedicated operation would express the cycle-breaking intent as one API operation and could use the direct buffer-detachment implementation where supported.
- Letting the array itself become unreachable is sufficient when possible, but not when it belongs to long-lived state or participates in the cycle that needs to be broken.
Additional context
This operation is intended for the end of an array's logical use, especially resource-management and coroutine/scheduler cleanup paths. It is not intended to replace clear() in reuse-heavy code where retaining capacity is desirable.
Is your feature request related to a problem? Please describe.
Array::clear()makes an array logically empty, but on non-JavaScript backends it intentionally retains the backing buffer and the references stored in its slots. This is useful when the capacity will be reused, but it is unsuitable when those references must be severed explicitly to break a cycle.One motivating case is a coroutine or scheduler state that owns an array-backed queue of callbacks/closures. The queued callbacks may capture the coroutine state, producing a cycle like:
When the coroutine is completely finished, emptying and detaching the queue can break this cycle and make the objects eligible for reclamation.
Array::release_unused(placeholder=...)can overwrite the retained slots afterclear(), but it requires a value ofT. For callback/function types and other reference-bearing types, there may be no canonical harmless default value. It also fills the entire unused capacity and retains the allocation.Describe the solution you'd like
Add an operation that empties an array and detaches its backing storage without requiring a placeholder. Tentatively, this could be named
Array::reset:The intended contract is:
length()is zero afterwards.capacity()becomes zero where capacity is meaningful).T,Defaultbound, or placeholder is required.Replacing the buffer directly also avoids explicitly overwriting every retained slot as
release_unuseddoes. Actual reclamation remains runtime-dependent, and an outstandingArrayViewmay keep the previous buffer reachable subject to the existing view-lifetime rules.The name is open for discussion. Since
reseton some existing buffer-like types means “become empty while retaining capacity,” a more explicit name such asclear_and_releaseorclear_and_shrinkmay communicate the storage behavior better.Describe alternatives you've considered
array.clear(); array.release_unused(placeholder=...)breaks references but requires a suitable placeholder, scans the unused capacity, and retains the allocation.array.clear(); array.shrink_to_fit()is semantically close and does not need a placeholder. A dedicated operation would express the cycle-breaking intent as one API operation and could use the direct buffer-detachment implementation where supported.Additional context
This operation is intended for the end of an array's logical use, especially resource-management and coroutine/scheduler cleanup paths. It is not intended to replace
clear()in reuse-heavy code where retaining capacity is desirable.