加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > Java > 正文

haskell – 使用O(1)函数为CString编写可存储的实例以获得总字节

发布时间:2020-12-15 02:29:52 所属栏目:Java 来源:网络整理
导读:我正在尝试为CString编写一个 storable vector实例(在我的例子中,以null结尾的C字符).可存储的实例将存储CString所指的指针(Ptr CChar).因此,向量的长度是CString指针的数量.现在,我写这个可存储实例的原因是因为它将用于从FFI CString进行零拷贝,然后使用un
我正在尝试为CString编写一个 storable vector实例(在我的例子中,以null结尾的C字符).可存储的实例将存储CString所指的指针(Ptr CChar).因此,向量的长度是CString指针的数量.现在,我写这个可存储实例的原因是因为它将用于从FFI CString进行零拷贝,然后使用unsafeCreate进行快速ByteString构建(在一些转换之后 – 所以,我们在这里使用快速向量进行中间操作).为了快速进行ByteString构建,可存储实例需要三件事:

>总长度(以字节为单位) – 可存储实例需要具有簿记分配,用于在将每个CString添加到向量时存储每个CString的长度,以及到目前为止存储的CString的总长度.让我们说C字符串的总长度不能超过2 ^ 31.因此,Int32 / Word32将用于存储每个CString的长度和总长度.
>存储CString的函数及其长度 – O(n)时间.此函数将遍历CString,并存储其长度,并且还将总长度增加CString的长度.
> Functon以总字节数返回长度 – O(1)时间.此函数将仅从存储总长度的字段中检索值

虽然我知道如何编写自定义可存储实例,但我不知道如何处理这种情况.一个简单的代码(可以是一个简单的玩具示例),显示如何进行自定义簿记,并写入存储/获取簿记结果的功能将非常感谢.

更新1(澄清)

在我的案例中使用可存储的矢量实例的原因有两个:使用未装箱类型的快速计算/转换(通过C FFI接收的实时数据),以及快速转换为bytestring(以实时发送数据) IPC到另一个程序).对于快速字节串转换,unsafeCreate非常好.但是,我们必须知道要分配多少,并且还要传递一个转换功能.给定一个可存储的向量实例(使用混合类型 – 我将上面的问题简化为CString类型),我很容易构建一个快速转换函数,它可以遍历向量的每个元素并将其转换为bytestring.然后,我们将它传递给unsafeCreate.但是,我们还必须传递它要分配的字节数. O(n)递归字节长度计算函数太慢,并且可以使构造字节串的开销加倍.

解决方法

听起来你想写这样的东西.请注意,此代码未经过测试.

-- The basic type.  Export the type but not the constructors or 
-- accessors from the module.
data StringVector {
   strVecLength :: Word32,-- Total length
   strVecContents [(Word32,Ptr CChar)]  -- (Length,value) pairs
}

-- Invariants: forall (StringVector len contents),--    len == sum (map fst) contents
--    all (p -> fst p == c_strlen (snd p)) contents


-- The null case.
emptyStrVec :: StringVector
emptyStrVec = StringVector 0 []


-- Put a new Cstring at the head of the vector.  Analogous to ":".
stringVectorCons :: Ptr CChar -> StringVector -> StringVector
stringVectorCons ptr (StringVector len pairs) = 
   StringVector (len + n) $(n,ptr) : pairs
   where
      n = c_strlen ptr   -- Or whatever the right function name is


-- Extract the head of the vector and the remaining vector.
stringVectorUncons :: StringVector -> ((Word32,Ptr CChar),StringVector)
stringVectorUncons (StringVector len (h:t)) =
   (h,StringVector (len - fst h) t)

之后,您可以根据应用程序添加您可能需要的任何其他功能.只需确保每个函数都保留不变量.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读