设计模式专题之C语言-三大属性

在C语言中,尽管没有直接的面向对象编程(OOP)特性如类和继承,但可以通过一些编程技巧模拟和实现这些特性。下面是从C语言的角度讲解继承、封装和多态的方法。

1.继承 (Inheritance)

继承是面向对象编程中的一个核心概念,用于实现类之间的层次结构。在C语言中,没有内建的继承机制,但可以通过结构体组合的方式来模拟继承。
模拟继承的方式:
基类和派生类:可以定义一个结构体作为“基类”,然后在另一个结构体中嵌套第一个结构体,模拟“派生类”。

1.1.举例

想象你在创建一系列的动物模型。在这些动物模型中,有些动物是通用的(比如所有动物都有的特征),而其他动物则在此基础上增加了自己的独特特征。

1.2.C语言模拟继承

  • 基本动物(基类):定义一个结构体,表示所有动物共有的特征。
  • 具体动物(派生类):在另一个结构体中包含基本动物的结构体,并添加特有的特征。

1.3.代码示例:

#include <stdio.h>

// 基类:动物
typedef struct {
    int age;
} Animal;

// 派生类:狗,继承了动物的特征,并添加了自己的特征
typedef struct {
    Animal animal;  // 继承基类
    int barkVolume;
} Dog;

int main() {
    Dog myDog;
    myDog.animal.age = 5;        // 访问继承的特征
    myDog.barkVolume = 10;       // 访问派生特征

    printf("My dog is %d years old and barks at volume %d.\n", myDog.animal.age, myDog.barkVolume);
    return 0;
}

解释:这里的 Dog 结构体包含了一个 Animal 结构体,这就好像 Dog 继承了 Animal 的特征,并且可以添加自己的特征(比如 barkVolume)。

2.封装 (Encapsulation)

封装是将数据和操作数据的函数捆绑在一起,并隐藏内部实现细节。C语言没有内建的封装机制,但可以通过使用static关键字和函数指针模拟。
模拟封装的方式:
私有和公共接口:可以将结构体定义和相关函数放在一个文件中(例如.c文件),而将接口函数声明放在另一个文件中(例如.h文件)。这样可以隐藏实现细节,只暴露公共接口。

2.1.举例

想象你在设计一个复杂的电子设备(比如智能手机)。你不需要知道设备内部的所有细节(例如如何电池工作),只需使用设备提供的接口(例如触摸屏、按钮)即可。

2.2.C语言模拟继承

  • 接口(公共):在一个头文件中定义你希望外部使用的函数。
  • 实现(私有):在另一个源文件中实现这些函数的具体细节,并隐藏内部细节。

2.3.代码示例:

// device.h
#ifndef DEVICE_H
#define DEVICE_H

typedef struct {
    int batteryLevel;
} Device;

void chargeDevice(Device* device, int amount);
int getBatteryLevel(const Device* device);

#endif // DEVICE_H
// device.c
#include "device.h"

static void internalFunction() {
    // 可能是内部的、复杂的功能
}

void chargeDevice(Device* device, int amount) {
    device->batteryLevel += amount;
    internalFunction();  // 内部函数的调用
}

int getBatteryLevel(const Device* device) {
    return device->batteryLevel;
}

解释:device.h 只提供了对外的接口,隐藏了内部的实现细节(如 internalFunction)。外部代码只需要关心如何使用 chargeDevice 和 getBatteryLevel 函数,而不必了解具体的实现。

3.多态 (Polymorphism)

多态允许以统一的接口处理不同类型的对象。在C语言中,多态通常通过函数指针来实现,可以实现类似于接口的功能。
模拟多态的方式:
函数指针和结构体:可以在结构体中定义函数指针,指向不同的实现函数,以实现不同的行为。

3.1.举例

想象你有一组不同的电器(比如电视、音响、空调),它们都有一个公共的开关按钮。尽管它们的内部工作方式不同,但你可以通过按下开关按钮来控制它们。

3.2.C语言模拟继承

  • 定义一个接口(开关按钮):使用函数指针来模拟不同的操作。
  • 具体实现(不同的电器):每种电器有自己独特的开关操作。

3.3.代码示例:

#include <stdio.h>

// 定义一个接口
typedef struct {
    void (*turnOn)();
} Appliance;

// 具体实现:电视
void tvTurnOn() {
    printf("TV is now ON.\n");
}

// 具体实现:音响
void speakerTurnOn() {
    printf("Speaker is now ON.\n");
}

int main() {
    Appliance tv;
    Appliance speaker;

    tv.turnOn = tvTurnOn;
    speaker.turnOn = speakerTurnOn;

    tv.turnOn();     // 输出: TV is now ON.
    speaker.turnOn(); // 输出: Speaker is now ON.

    return 0;
}

解释:这里的 Appliance 结构体包含一个函数指针 turnOn。不同的电器(tv 和 speaker)实现了不同的 turnOn 函数。你可以通过调用 turnOn 来启动不同的电器,而无需关心它们的具体实现。

4.总结

继承:通过结构体嵌套来模拟继承关系。
封装:通过将结构体和相关函数分开并使用static关键字隐藏实现细节来实现封装。
多态:通过在结构体中使用函数指针来实现不同的行为。
尽管C语言没有直接的面向对象特性,通过以上技巧,可以在C语言中实现类似于OOP的设计模式和机制。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

甜航一直在

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值