【问题标题】:C structs using self使用 self 的 C 结构
【发布时间】:2014-06-02 10:45:58
【问题描述】:

我有一些程序为我生成的代码,我真的不明白为什么它会这样做。语言是纯 C 语言,生成一个结构体。

.h 文件:

struct X_IMPL {
   sint32 y;
};

struct X {
   struct X_IMPL * IMPL;
};

.c 文件:

#define _my_y self->IMPL->y

sint32 do_something(struct X * self)
{
    return _my_y*13;
}

我确实假设_my_y 现在指向结构内的一个变量,并且可以用来更改结构的变量。我的问题是,为什么会以这种方式生成代码?与仅使用参数的引用相比有什么优势吗?当使用这样的定义创建引用时,我真的需要那个参数吗?

【问题讨论】:

  • 我不太明白你的问题。 #define 不会“创建”任何东西,它只是一个文本替换宏。如果源有_my_y,编译器将看到self->IMPL->y。也不确定在这种情况下您所说的“参考”是什么意思。
  • 它所做的只是减少代码的冗长(想象一下,如果你在do_something 中有很多代码,那么到处都有self->IMPL->y 可能会变得重复。也就是说,在宏后面隐藏这样的东西是通常被认为是不好的做法(至少对于人类编写的代码而言!)。
  • @unwind:作为参考,我的意思是my_yself->IMPL->y 将指向内存中的同一个位置。
  • @Pphoenix 我认为您并没有真正理解这段代码中发生了什么。 _my_y 在编译后的程序中不作为符号存在;它是#define 的名称,因此它将被预处理器替换,编译器永远不会看到它。尝试读取预处理器输出(-E 使用 gcc)。
  • 宏需要变量self 在使用它的地方可用,是的。在这样的代码(C 中的面向对象函数)中,您必须始终传递一个指向该方法应该操作的对象的 self(或 this)指针。

标签: c struct reference c-preprocessor self


【解决方案1】:

这只是偏好问题,因为您可以通过多种方式做到这一点,但这并不是那么纯粹。在第一行,define 所在的地方,它只定义了一个宏,用于通过结构指针访问结构指针。

【讨论】:

    【解决方案2】:

    我认为您所看到的是 C 中的“面向对象编程”。请注意,它通常与 C++/Java/C#/whatever 中的 OOP 不是 1:1 等效的,因为 OOP 机制不是内置的,而是实现的明确地。因此,不同的项目和不同的开发人员可能会为同一件事编写完全不同的代码,而在其他具有内置 OOP 功能的语言中,他们都会以相同的方式使用内置功能。

    C++ 中的do_something 可能如下所示:

    // do_something is public member function AKA method of class X
    sint32 X::do_something()
    {
        // y is this->y, private member variable of class X
        return y * 13; 
    }
    

    【讨论】:

    • 如果是这个原因,那么它是一个糟糕的工具。 C 中的真正 OOP 要么以某种方式使用函数指针,要么(更有可能)将成员函数实现为以结构指针作为参数的普通函数,其中结构指针的类型不完整,调用者不知道其内容。然后函数的内部是无关紧要的,#define 只是混淆。我宁愿怀疑 #define 是为了简化以适应某种给定的 API。
    • @Lundin 显示的代码太少,可能与真实代码不是100%相同,我不会通过“OOP纯度”的判断。 do_something 很像用 C 编写的“类 X 的成员函数”,隐含含义的 self 参数有点赠品。是的,我同意在生成的代码中使用那种#define 有点WTF(除非有一些外部原因)。
    • 是的,这不是完整的项目(这是巨大的)。 X 也是另一个名字,但它太长了,读起来会很混乱,所以我用更易读的东西代替了它:)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-07-25
    • 2018-04-25
    • 1970-01-01
    • 1970-01-01
    • 2014-07-06
    相关资源
    最近更新 更多