Skip to content

Vec::reserve should use alloc_excess #71383

Open
@hsivonen

Description

@hsivonen

When calling reserve() on a Vec whose capacity is zero, afterwards the capacity() method always returns the exact argument that was passed to reserve(). Even though the contract of reserve() allows Vec to make the capacity larger than requested, if the previous capacity is zero, Vec does not make use of this. When the underlying allocator is bucketed, rounding to the bucket size never wastes memory, so Vec should use alloc_excess to make the slop available to the user.

Use case: We're going to write at least best_case items and at most worst_case items, such that best_case < worst_case, but we don't know how many items exactly. The common case can be expected to be close to best_case but often at least one more. It would make sense to first allocate for best_case rounded up to allocator bucket size, then start writing, then if not everything fits, resize to worst_case, write the rest, and finally resize to the size actually written and shrink_to_fit().

This would guarantee at most three allocations and in the common case one.

This issues comes up often with low-level string code.

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-allocatorsArea: Custom and system allocatorsA-collectionsArea: `std::collections`C-enhancementCategory: An issue proposing an enhancement or a PR with one.T-libs-apiRelevant to the library API team, which will review and decide on the PR/issue.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions