C语言中使用“结构体 + 函数指针”来模拟面向对象编程(OOP

C语言中使用“结构体 + 函数指针”来模拟面向对象编程(OOP)的“对象 + 方法”
是C语言中最经典、最常见的“伪OOP”写法之一。

这种写法在很多嵌入式系统、游戏引擎、图形库、驱动程序、GUI框架中都被广泛使用(GTK、libuv、SDL、Linux内核的部分模块等都大量使用类似手法)。

核心思想

把“数据”和“能作用在这份数据上的行为(函数)”打包放在一起。

typedef struct {
    // 数据成员
    int x;
    int y;
    
    // 方法(函数指针)
    void (*move)(void* self, int dx, int dy);   // 第一个参数通常放自己
    void (*print)(const void* self);
    double (*distance_to_origin)(const void* self);
} Point;

最常见的几种写法对比(由简到复杂)

写法编号风格self 参数写法推荐场景易读性维护性
1显式传 selfvoid (*func)(void* self, ...)初学者、教学★★★☆☆★★★☆☆
2用宏隐藏 self#define this self个人项目、追求简洁★★★★☆★★☆☆☆
3强类型 self(推荐)void (*func)(This* self, ...)中大型项目、库设计★★★★★★★★★★
4带继承(虚函数表)vtable + 结构体开头需要多态的复杂系统★★★☆☆★★★★☆

下面我们用最推荐的第3种写法(强类型 self)来完整举例:

推荐写法示例(2024-2025年主流做法)

#include <stdio.h>
#include <math.h>
#include <stdlib.h>

// 前向声明
typedef struct Point Point;

// ==================== 1. 定义“类”(结构体) ====================
struct Point {
    // 数据部分
    float x;
    float y;

    // 方法表(函数指针)
    void    (*move)(Point* self, float dx, float dy);
    void    (*print)(const Point* self);
    float   (*distance_to)(const Point* self, const Point* other);
    void    (*destroy)(Point* self);   // 类似析构函数
};


// ==================== 2. 方法实现 ====================

static void point_move(Point* self, float dx, float dy) {
    self->x += dx;
    self->y += dy;
}

static void point_print(const Point* self) {
    printf("Point(%.2f, %.2f)\n", self->x, self->y);
}

static float point_distance_to(const Point* self, const Point* other) {
    float dx = self->x - other->x;
    float dy = self->y - other->y;
    return sqrtf(dx*dx + dy*dy);
}

static void point_destroy(Point* self) {
    // 如果有动态分配的成员,这里释放
    // 这里只是示例,实际可以 free(self) 如果是堆上创建的
    printf("Point at %p destroyed\n", (void*)self);
    // free(self);   // 如果是用 malloc 创建的才需要
}


// ==================== 3. 构造函数(工厂函数) ====================

Point* point_new(float x, float y) {
    Point* p = malloc(sizeof(Point));
    if (!p) return NULL;

    // 初始化数据
    p->x = x;
    p->y = y;

    // 绑定方法(最关键一步)
    p->move        = point_move;
    p->print       = point_print;
    p->distance_to = point_distance_to;
    p->destroy     = point_destroy;

    return p;
}


// ==================== 4. 使用方式 ====================

int main() {
    Point* p1 = point_new(3, 4);
    Point* p2 = point_new(0, 0);

    if (!p1 || !p2) {
        printf("内存分配失败\n");
        return 1;
    }

    p1->print(p1);                // Point(3.00, 4.00)
    p1->move(p1, 1, -2);
    p1->print(p1);                // Point(4.00, 2.00)

    printf("距离原点: %.2f\n", p1->distance_to(p1, p2));

    p1->destroy(p1);
    p2->destroy(p2);

    free(p1);
    free(p2);

    return 0;
}

更简洁但牺牲类型安全的写法(风格1)

很多人教学时会这样写(初学者常见):

typedef struct {
    int x, y;
    void (*move)(void* self, int dx, int dy);
    void (*show)(void* self);
} Shape;

void shape_move(void* self, int dx, int dy) {
    Shape* s = (Shape*)self;
    s->x += dx;
    s->y += dy;
}

带“继承”与多态的进阶写法(简版)

typedef struct {
    // 虚函数表必须放在最前面
    struct {
        void (*draw)(void* self);
        void (*move)(void* self, int dx, int dy);
    } vtable;

    int x, y;
    // ... 公共数据
} Shape;

typedef struct {
    Shape base;
    int radius;
} Circle;

void circle_draw(void* self) {
    Circle* c = self;
    printf("Circle at (%d,%d) r=%d\n", c->base.x, c->base.y, c->radius);
}

还有(简单版 / 推荐强类型版 / 带继承的多态版 / 其他变种)

内容概要:本文介绍了一项创新性未发表的研究,即利用多元宇宙优化算法(Multiverse Optimizer, MVO)对分时电价下的需求响应与综合能源系统调度问题进行建模与求解,旨在实现能源系统的经济性、高效性与可持续性运行。该研究构建了包含多种能源设备(如光伏、风机、燃气轮机、储能系统等)及可调节负荷的综合能源系统模型,充分考虑了用户侧的需求响应行为在分时电价机制下的响应特性,通过MVO算法对系统运行成本、能源利用率、碳排放等多目标进行协同优化,实现了日前调度计划的智能决策。研究还提供了完整的MATLAB代码实现,便于研究人员复现实验、验证算法性能,并为进一步研究提供可靠的仿真基础。; 适合人群:具备一定电力系统、优化算法及MATLAB编程基础的科研人员、研究生以及从事能源互联网、综合能源系统规划与运行的技术工程师。; 使用场景及目标:① 学习并掌握多元宇宙优化算法在复杂能源系统调度中的具体应用方法;② 研究分时电价机制如何通过需求响应引导用户参与电网互动,实现削峰填谷;③ 实现综合能源系统(IES)中冷、热、电、气等多种能源的协同优化调度,以降低运行成本、提高新能源消纳能力和系统可靠性;④ 为相关领域的学术研究提供可复现的代码实例和仿真平台。; 阅读建议:此资源以MATLAB代码为核心载体,深入剖析了算法应用与系统建模的全过程。建议读者在学习时,不仅应关注代码的实现细节,更要理解其背后的数学模型、优化目标设定和约束条件的物理意义。建议结合文档中的模型描述,逐步调试代码,观察不同参数和场景下的优化结果,从而深刻掌握综合能源系统优化调度的设计思想与关键技术。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值