gpt4 book ai didi

c++ - 将非拥有位容器基于 std::vector 是个好主意吗?标准::跨度?

转载 作者:行者123 更新时间:2023-11-30 05:00:22 26 4
gpt4 key购买 nike

在我的几个项目中,我越来越需要高效地处理内存中的连续位序列 (*)。到目前为止,我已经编写了一堆可内联的独立函数,以选择“位容器”类型(例如 uint32_t )为模板,用于获取和设置位,将“或”和“和”应用于它们的值,定位容器,将以位为单位的长度转换为以字节为单位的大小或以容器为单位的长度,等等……看起来是时候编写类了。

我知道 C++ 标准库有一个专门化的 std::vector<bool> ,许多人认为这是一个设计缺陷——因为它的迭代器不公开实际的 bool ,而是代理对象。无论这对于特化来说是好主意还是坏主意,这绝对是我正在考虑的东西 - 一个显式位代理类,希望“总是”被优化掉(用 constexprnoexceptinline 进行很好的润滑) .因此,我在考虑是否可以从一个标准库实现中改编 std::vector 代码。

另一方面,我的预期类(class):

  • 永远不会拥有数据/位 - 它将收到起始位容器地址(假设对齐)和位长度,并且不会分配或释放。
  • 它将无法动态或以其他方式调整数据大小——即使保留与 std::vector::resize() 相同的空间量也不行;它的长度将在其生命周期/范围内固定。
  • 它不应该对堆有任何了解(并且在没有堆时工作)

从这个意义上说,它更像是位的跨度类。那么也许从跨度开始?我不知道,跨度仍然不标准;跨度中没有代理...

那么什么是我实现的良好基础(编辑: 不是基类)? std::vector<bool>std::span ?两个都?没有任何?或者 - 也许我正在重新发明轮子,而这已经是一个已解决的问题?

注意事项:

  • 位序列长度在运行时已知,而不是编译时;否则,正如@SomeProgrammerDude 建议我可以使用 std::bitset
  • 我的类(class)不需要“成为”span 或“成为” vector ,所以我不打算专门化它们中的任何一个。

(*) - 到目前为止,SIMD 效率不高,但可能稍后会出现。此外,这可以用在 CUDA 代码中,我们不进行 SIMDize,但假装 channel 是正确的线程。

最佳答案

而不是 std::vectorstd::span我怀疑你的类的实现会与 std::bitset 有更多共同点。 ,因为它几乎是同一件事,除了(固定的)运行时确定的大小。

事实上,您可以采用典型的 std::bitset实现并移动 <size_t N>类中的模板参数作为 size_t size_成员(或任何你喜欢的名字),你将拥有几乎没有变化的动态位集类。你可能想摆脱任何你认为笨拙的东西,比如采用 std::string 的构造函数。和 friend 。

最后一步是移除底层数据的所有权:基本上,您将移除构造函数中底层数组的创建,并使用一些指针维护现有数组的 View 。

如果您的客户不同意用于存储的底层无符号整数类型(您称之为“位容器”),那么您可能还需要使您的类成为该类型的模板,尽管如果这样会更简单每个人都同意说uint64_t .

至于std::vector<bool>去吧,你不需要太多:所有vector是你想要的吗,std::bitset可能也是如此:vector 的主要内容adds 是动态增长 - 但你说过你不想要那个。 vector<bool>具有代表单个位的代理对象概念,但std::bitset也是如此.

来自 std::span您认为底层数据没有所有权,但我认为这实际上并不代表很多底层代码。您可能需要考虑 std::span 编译时已知大小 运行时提供的大小(由 Extent == std::dynamic_extent 表示)的方法,如果这对您有用(主要是如果您有时使用 compile -time 大小,并且可以专门化一些方法以在这种情况下更有效)。

关于c++ - 将非拥有位容器基于 std::vector<bool> 是个好主意吗?标准::跨度?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50846848/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com