Skip to content

Can immer::vector support incomplete types with sizes known at compile time? #320

Description

@aimoonchen

test code:

#include <immer/box.hpp>
#include <immer/map.hpp>
#include <immer/vector.hpp>

#include <cstdio>
#include <string>

template <typename T>
struct size_traits {
    static constexpr std::size_t value = sizeof(T);
};

template <std::size_t Size>
constexpr auto derive_bl() {
    constexpr std::size_t space = 264;
    constexpr std::size_t full_elems = space / Size;
    if constexpr (full_elems >= 256) return 8;
    else if constexpr (full_elems >= 128) return 7;
    else if constexpr (full_elems >= 64) return 6;
    else if constexpr (full_elems >= 32) return 5;
    else if constexpr (full_elems >= 16) return 4;
    else if constexpr (full_elems >= 8) return 3;
    else if constexpr (full_elems >= 4) return 2;
    else if constexpr (full_elems >= 2) return 1;
    else return 0;
}

struct Value;

template <>
struct size_traits<Value> {
    static constexpr std::size_t value = 16;
};

using ValueVector =
    immer::vector<Value, immer::default_memory_policy, immer::default_bits, derive_bl<size_traits<Value>::value>()>;
using ValueVectorPtr = immer::box<ValueVector>;

struct Value {
    int data;
    ValueVectorPtr vec;
};

static_assert(sizeof(Value) == size_traits<Value>::value);

int main() {
    printf("sizeof(Value) = %zu\n", sizeof(Value));

    Value root{42, {}};
    auto vec = ValueVector{}.push_back(Value{1, {}}).push_back(Value{2, {}});
    root.vec = ValueVectorPtr{vec};

    printf("root.vec.get().size() = %zu\n", root.vec.get().size());
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions