Кольцевой буфер без unsafe: чем пришлось заплатить
Большинство кольцевых буферов хранят элементы в MaybeUninit<T>, и читать такую память можно только в unsafe. Мне хотелось обойтись без этого.
Читать дальшеСвернуть
В tc-ring слоты хранятся как [Option<T>; N]: каждый либо пуст, либо содержит значение. Массив создаётся через std::array::from_fn(|_| None), и для этого не нужно, чтобы T был Copy или Default.
Цена такого решения: Option<T> бывает больше, чем T. Для ссылок, Box и NonZero-типов компилятор прячет признак «пусто» в недопустимом значении, и размер не меняется. Для u32 или f64 каждый слот вырастает за счёт выравнивания.
Индексы считаются как (head + i) % N. Раз N известен на этапе компиляции, при степени двойки деление по модулю превращается в обычную битовую маску, так что отдельная оптимизация не понадобилась.