如何在不使用Malloc的情况下使typedef尽可能私有?

时间:2015-07-06 19:19:39

标签: c plc

我正在寻找一种方法来创建只能从一组特定的函数调用(setBit(bit_typ * const t),getBit(bit_typ * const t))访问或操作的私有样式typedef。我正在寻找一种不使用malloc的方法,有没有人有任何想法?

编辑://这个问题与this one不同,因为它正在寻找方法来接近"私人"结构而另一个问题(TL; DR是否有一种方法来定义一个opaque类型,它仍然可以在堆栈上分配,而且不会破坏严格的别名规则?)寻找一个解决问题的方法来解决与我的问题的一个可能的解决方案。

1 个答案:

答案 0 :(得分:5)

一种方法是公开opaque类型的总 size ,并使用use将opaque类型的对象声明为unsigned char [N]缓冲区。例如,假设您有一些类型OpaqueType,其内部要隐藏用户。

在头文件中(向用户公开),你可以这样做

typedef unsigned char OpaqueType[16];

其中16是要隐藏的类型的确切字节大小。在头文件中,您可以根据该类型编写整个接口,例如

void set_data(OpaqueType *dst, int data);

在实现文件中,您声明实际类型

typedef struct OpaqueTypeImpl
{
  int data1;
  double data2;
} OpaqueTypeImpl;

并实现以下功能

void set_data(OpaqueType *dst, int data)
{
  OpaqueTypeImpl *actual_dst = (OpaqueTypeImpl *) dst;
  actual_dst->data1 = data;
}

您还可以添加静态断言,以确保sizeof(OpaqueType)sizeof(OpaqueTypeImpl)相同。

当然,正如下面的评论中所指出的那样,必须采取额外的步骤来确保这些对象的正确对齐,例如C11中的_Alignas或者#34;中的某些基于联合的技术。经典"下进行。

通过这种方式,您可以让用户有机会声明OpaqueType的非动态对象,即您不会强制用户在内部调用将malloc此类对象的函数。与此同时,您不会向用户展示有关您的类型内部结构的任何信息(除了它的总大小和对齐要求)。

另请注意,以这种方式声明的OpaqueType是一个数组,这意味着它不可复制(除非您使用memcpy)。如果您想积极阻止无限制的用户级复制,这可能是一件好事。但是,如果要启用复制,可以将数组包装到结构中。

这种方法并不是非常优雅,但是当你想要保持你的类型的对象可由用户自定义时,这可能是隐藏实现的唯一方法。