0

我有一种类型的字符串,它知道它们的大小,称为pstring(对 Pascal 字符串的眨眼)。而不是 struct {size, p_bytes},大小只是在内存中以字节数组为前缀。(原因是在概念上和实践上都避免双重引用;以及结构和字节数组的双重堆分配。)我可以使用工具 func 来做到这一点,只是分配sizeof(size_t)更多字节,返回指向实际地址的指针字节数组,并提供一个宏来读取几个字节之前的大小。

相反,我想通过使用灵活数组成员的“灵活结构”在稍高的级别上做到这一点:

typedef struct {
    size_t   size;
    uint     hash;
    char     bytes[];
} PString;
// constructor:
PString * pstring (char * bytes, size_t size) {...}

(那些 pstrings 也有一个散列,因为它们被困在一个池中。)但是现在,我有一个形而上学的问题来选择对 pstrings 的正确访问。问题在于 pstrings(就像普通字符串一样)只能通过指针进行操作。但是我应该如何提供接口,指向与否?

  • 字符串通常是隐式指向的,其类型如const char * string;, 因此也“指向” pstring 类型似乎很自然,而且每个人都知道它是指针类型。
  • 但是,在使用结构时,通常的做法是(我猜)不要隐式指向变量(通过指向类型),而是用 a 显式声明变量*(有时在它们的名称前面加上'p_')。

那么,在这里我应该怎么做,让 pstrings 的用户在语义上清楚并且在实践中感到轻松?

在任何情况下,指向一个 var 并且字段访问通过->. 到目前为止,如您所见,我选择了第二个选项:人们将 pstring 声明为PString * ps;. 但我准备根据以下论点进行更改:

  • 一个 pstring var 根本不能是无指向的(甚至比普通字符串还要少,因为通过 struct copy 我们会丢失字节 --> hello segfault)。
  • “pstring”中的“p”可以作为“pointed”的提醒。

你怎么看?

4

3 回答 3

1

我不喜欢灵活的数组成员,但既然你选择了这种方法,我会保持它的指针性质可见,只是因为它对使用它的人来说更诚实/更清楚。

于 2012-12-13T14:05:31.100 回答
1

在我看来,你最好采用第二种方法。

在隐式指针“C”字符串的情况下,它们的行为类似于字节数组,您可以在其中直接从字节 1 开始访问字符串内容。但是,在这种情况下,它是一种构造(用户定义)类型,并且要进行区分,我希望它是一个显式指针(即第二种方法)。

顺便说一句,您会提供对这些字符串执行比较、字符搜索等操作的功能吗?我建议您可以遵循 C++ 字符串类型的模型并提供一个 c_str 函数,该函数进一步提供指向“字节”的指针。

于 2012-12-13T14:03:26.750 回答
0

我建议坚持您当前的选项(使指针明确)。您的库的用户必须知道它无论如何都是一个指针(例如,使用->它,知道使用赋值只会创建一个浅拷贝),所以它只会混淆试图隐藏它的事情。

标准库还提供了这种方法的一个示例 -FILE类型必须始终用作FILE *.

于 2012-12-13T21:20:07.640 回答