嵌入式八股C语言---面向对象篇

devtools/2025/3/14 11:35:35/

面向对象与面向过程

  • 面向过程
    就是把整个业务逻辑分成多个步骤,每步或每一个功能都可以使用一个函数来实现
  • 面向对象
    对象是类的实例化,此时一个类就内部有属性和相应的方法

封装

  在C语言里实现封装就是实现一个结构体,里面包括的成员变量和函数指针,然后在构造函数中,为结构体的函数指针赋初值
对于这个函数指针往往会把自身传入,因为只是在模仿class

#include <stdio.h>
#include <stdlib.h>
struct student
{int height;char* name;void(*add_height)(struct student *, int);
};void ADD_HEIGHT(struct student * stu, int add)
{stu->height += add;
}
struct student * Student(int height,char *name)
{struct student * stu = malloc(sizeof(struct student));if(stu) {stu->height = height;stu->name = name;stu->add_height = ADD_HEIGHT;}return stu;
}
void freeStudent(struct student * stu )
{if(stu) {free(stu);stu = NULL;}
}
int main()
{struct student * stu = Student(180,"LCS");printf("%d\r\n",stu->height);stu->add_height(stu,50);printf("%d\r\n",stu->height);return 0;
}

继承

  • 实现方案一: 子类中嵌套父类结构体指针
    C语言模仿继承就是子类的结构体里嵌套一个父类的结构体
    那如何实现类似虚函数的效果呢–修改父类的函数指针的指向就行
 		#include <stdio.h>#include <stdlib.h>struct animal{/* data */int age;void (*speak)(void);};void cat_speak() {printf("speak miaomiao\r\n");}void dog_speak() {printf("speak wangwang\r\n");}struct cat {struct animal * anm;int like_nothing;};struct dog {struct animal * anm;int like_eat_shit;};struct animal* Animal(int age) {struct animal* anm = malloc(sizeof(struct animal));anm->age = age;anm->speak = NULL;return anm;}struct cat* Cat(int age) {struct cat* new_cat = malloc(sizeof(struct cat));new_cat->anm = Animal(age); // 这就意味着等会你释放内存是真麻烦new_cat->like_nothing = 1;new_cat->anm->speak = cat_speak;return new_cat;}struct dog* Dog(int age) {struct dog* new_dog = malloc(sizeof(struct dog));new_dog->anm = Animal(age); // 这就意味着等会你释放内存是真麻烦new_dog->like_eat_shit = 1;new_dog->anm->speak = dog_speak;return new_dog;}int main(){struct cat* new_cat = Cat(5);struct dog* new_dog = Dog(10);new_cat->anm->speak();new_dog->anm->speak();return 0;}
  • 继承的妙用: struct list_head 双向链表
      当我们想要实现自己的列表的实现 就把自己的链表中嵌入这个双向列表就行
  • 实现方案二: 父类提供一个void * 私有指针 不同的子类把void * 做不同的实现
#include <stdio.h>
#include <stdlib.h>// 基类定义
typedef struct {int age;void (*speak)(void*); // 虚函数指针void* private_data;   // 用于存储子类特定数据
} Animal;// Cat的私有数据结构
typedef struct {int like_nothing;
} CatPrivate;// Dog的私有数据结构
typedef struct {int like_eat_shit;
} DogPrivate;// 实现虚函数:猫叫声
static void cat_speak(void* obj) {CatPrivate* private_data = ((Animal*)obj)->private_data;printf("Cat says: miaomiao, like_nothing=%d\n", private_data->like_nothing);
}// 实现虚函数:狗叫声
static void dog_speak(void* obj) {DogPrivate* private_data = ((Animal*)obj)->private_data;printf("Dog says: wangwang, like_eat_shit=%d\n", private_data->like_eat_shit);
}// 创建Animal实例
Animal* create_animal(int age, void (*speak_func)(void*), void* private_data) {Animal* animal = malloc(sizeof(Animal));animal->age = age;animal->speak = speak_func;animal->private_data = private_data; // 设置私有数据return animal;
}// 创建Cat实例
Animal* create_cat(int age) {CatPrivate* cat_private = malloc(sizeof(CatPrivate));cat_private->like_nothing = 1; // 设定Cat私有数据Animal* animal = create_animal(age, cat_speak, cat_private);return animal;
}// 创建Dog实例
Animal* create_dog(int age) {DogPrivate* dog_private = malloc(sizeof(DogPrivate));dog_private->like_eat_shit = 1; // 设定Dog私有数据Animal* animal = create_animal(age, dog_speak, dog_private);return animal;
}int main() {Animal* new_cat = create_cat(5);Animal* new_dog = create_dog(10);// 调用虚函数new_cat->speak(new_cat);new_dog->speak(new_dog);// 清理资源free(((CatPrivate*)new_cat->private_data));free(((DogPrivate*)new_dog->private_data));free(new_cat);free(new_dog);return 0;
}
  • 继承与抽象类
      含有纯虚函数的类,我们一般称之为抽象类。抽象类不能被实例化,实例化也没有意义,唯一的好处就是代码分层

  • 公共继承 私有继承 保护继承
    在这里插入图片描述

  • 组合优于继承?

多态

  用父类指针调用子类的成员函数
  那就是给结构体的成员变量的函数指针指向不同的函数

深浅拷贝

  浅拷贝只是对指针的拷贝,拷贝后两个指针指向同一个内存空间,
  深拷贝不但对指针进行拷贝,而且对指针指向的内容进行拷贝,经深拷贝后的指针是指向两个不同地址的指针


http://www.ppmy.cn/devtools/167010.html

相关文章

双 Token 无感刷新机制在前后端分离架构中实现

在前后端分离的架构中&#xff0c;双 Token 无感刷新是一种常见的身份验证机制&#xff0c;用于在 Access Token 过期时&#xff0c;通过 Refresh Token 自动获取新的 Access Token&#xff0c;从而避免用户频繁登录。 1. 双 Token 无感刷新的核心流程 1.1 核心流程 用户登录&…

i18n的替换处理

i18n的替换处理 背景描述 在开发的过程中&#xff0c;需要对项目文件的中文使用i18n进行多语言处理。在特定的页面&#xff0c;中文会有特定的处理&#xff0c;例如: 存在5台设备&#xff0c;其中 5 是一个变量&#xff0c;同时具有特定的样式&#xff0c;那么这个时候应该如何…

网络空间安全(28)风险评估实施

前言 风险评估的实施是一个系统而细致的过程&#xff0c;旨在全面识别、评估潜在风险&#xff0c;并制定相应的风险管理策略。 一、确定评估范围和目标 评估范围&#xff1a; 明确评估的对象和范围&#xff0c;如特定的业务流程、项目、设备配置、信息系统等。确定评估的时间范…

深度学习笔记35_Inception v1算法实战与解析

&#x1f368; 本文为&#x1f517;365天深度学习训练营 中的学习记录博客&#x1f356; 原作者&#xff1a;K同学啊 | 接辅导、项目定制 一、我的环境&#xff1a; 1.语言环境&#xff1a;Python 3.8 2.编译器&#xff1a;Pycharm 3.深度学习环境&#xff1a; torch1.12.1cu11…

ChatGPT、DeepSeek、Grok 三者对比:AI 语言模型的博弈与未来

&#x1f4dd;个人主页&#x1f339;&#xff1a;一ge科研小菜鸡-CSDN博客 &#x1f339;&#x1f339;期待您的关注 &#x1f339;&#x1f339; 1. 引言 随着人工智能技术的飞速发展&#xff0c;AI 语言模型已经成为人机交互、内容创作、代码生成、智能问答等领域的重要工具…

国产编辑器EverEdit - 工具栏自定义及认识工具栏上的按钮

1 设置-高级-工具条 1.1 设置说明 1.1.1 工具条自定义 选择主菜单工具 -> 设置 -> 常规&#xff0c;在弹出的选项窗口中选择工具条分类&#xff0c;如下图所示&#xff1a; 左侧窗口是当前支持所有功能按钮列表(上图中居中栏)&#xff0c;右侧的窗口是当前显示在工具栏…

oXygen XML Editor—— XML编辑与结构化内容管理的优秀工具

Oxygen XML Editor是用于XML创作和开发的重要工具&#xff0c;为所有用户&#xff08;从初学者到专家&#xff09;量身定制的&#xff0c;它是通用的、跨平台的&#xff0c;并且可以作为独立应用程序和Eclipse插件使用。凭借对XML技术的强大支持&#xff0c;它提供了易于创建、…

TightVNC服务端安装与配置:Windows远程桌面的内网穿透解决方案

文章目录 前言1. 安装TightVNC服务端2. 局域网VNC远程测试3. Win安装Cpolar工具4. 配置VNC远程地址5. VNC远程桌面连接6. 固定VNC远程地址7. 固定VNC地址测试 前言 在现代快节奏的工作和生活中&#xff0c;跨地理界限的高效协作变得越来越重要。无论是远程办公、技术支持还是家…