面向对象编程思想

1.前言

        模块化的编程思想虽然可以很好的管理项目和具有比较好的移植性,但是为了更好的管理项目,使项目更具有移植性和更便于管理,我们引入面向对象编程思想。块化设计思想本质上是面向过程的思想,面向对象的设计思想更符合人类的思考习惯,面向对象编程就是将事物抽象为“对象” ,针对“对象”持有的数据和与之相关的行为进行编程。

2.面向对象的三大特征

封装:将不需要外部看到的数据和对应的方法放到类中,只需要暴露外部需要看到的数据和方法     ,根据事物特征进行分类封装,是从“代码手段/方法层面”将相关的数据和对应的方法集中一 起,让程序聚合成类和对象的基本单元。

继承:依据相关类的共有特征进行层级分类:GPIO->LED,GPIO->按键,UART->WiFi 。子类继承父类的特征,还可以有自己的独立特征,从“核心行为层面”给与了类聚合相关特征、灵活分类的能力。

多态:相同的特征在不同情况下有不同的表现,从“应用结果和表现层面”,描述了基于分类带来的益处,也就是可拓展性和可复用性。

3.分层设计

        为了便于面向对象的管理和理解,提出分层设计。最底层是硬件抽象层HAL层,分层结构的中心点其实是设备管理层,设备管理层写出对应的抽象类,然后设备驱动层对设备管理层进行继承,应用层直接调用设备管理层进行设备的操作,几乎能实现代码的完全移植。

4.GPIO设备对象的封装和管理

4.1 devices层

        首先 ,分析GPIO的数据特征:引脚号、端口号,GPIO行为特征:初始化、输出电平、读取电平,然后通过链表进行管理,所以得出以下GPIO对象。

typedef struct GPIODev{
    char *name;
    void *port;
    unsigned char pin;
    int (*Init)(struct GPIODev *ptdev);
    int (*Write)(struct GPIODev *ptdev, unsigned char status);
    int (*Read)(struct GPIODev *ptdev);
    struct GPIODev *next;
}GPIODevice;

        接着我们要对GPIO对象进行管理。所以我们在devices层分别编写代码如下,分别为dev_gpio.c和dev_gpio.h。

/*dev_gpio.c*/
#include "dev_gpio.h"
#include "mytype.h"
#include "string.h"
#include "drivers.h"

static GPIODevice *gHeadDevice = NULLDEV;

void IODeviceRegister(void)
{
    GPIODeviceCreate();
}

void IODeviceInsert(GPIODevice *ptdev)
{
    if(NULLDEV == ptdev)
    {
        gHeadDevice = ptdev;
    }
    else
    {
        ptdev->next = gHeadDevice;
        gHeadDevice = ptdev;
    }
}

GPIODevice *IODeviceFind(const char *name)
{
    GPIODevice *ptdev = gHeadDevice;
    while(NULLDEV != ptdev)
    {
        if(strstr(name,ptdev->name))
        {
            return ptdev;
        }
        ptdev = ptdev->next;
    }
    
    return NULLDEV;
}    

/*dev_gpio.h*/
#ifndef __DEV_GPIO_H
#define __DEV_GPIO_H

typedef struct GPIODev{
    char *name;
    void *port;
    unsigned int pin;
    int (*Init)(struct GPIODev *ptdev);
    int (*Write)(struct GPIODev *ptdev,unsigned char status);
    int (*Read)(struct GPIODev *ptdev);
    struct GPIODev *next;
}GPIODevice;

void IODeviceRegister(void);
void IODeviceInsert(GPIODevice *ptdev);
GPIODevice *IODeviceFind(const char *name);

#endif  /* __DEV_GPIO_H*/
 4.2 drivers层

        驱动层继承设备层,此层创建一个单独的gpio_config.h和drv_led.c和drv_led.h,代码分别如下。

/*gpio_config.h*/
#ifndef __GPIO_CONFIG_H
#define __GPIO_CONFIG_H

#define D1          \
{                   \
    .name = "D1",   \
    .port = GPIOB,  \
    .pin = GPIO_PIN_12, \
    .Init = GPIODrvInit, \
    .Write = GPIODrvWrite,   \
    .Read = GPIODrvRead, \
    .next = NULL    \
}

#define D2          \
{                   \
    .name = "D2",   \
    .port = GPIOB,  \
    .pin = GPIO_PIN_13, \
    .Init = GPIODrvInit, \
    .Write = GPIODrvWrite,   \
    .Read = GPIODrvRead, \
    .next = NULL    \
}

#define D3          \
{                   \
    .name = "D3",   \
    .port = GPIOB,  \
    .pin = GPIO_PIN_14, \
    .Init = GPIODrvInit, \
    .Write = GPIODrvWrite,   \
    .Read = GPIODrvRead, \
    .next = NULL    \
}

#define D4          \
{                   \
    .name = "D4",   \
    .port = GPIOB,  \
    .pin = GPIO_PIN_15, \
    .Init = GPIODrvInit, \
    .Write = GPIODrvWrite,   \
    .Read = GPIODrvRead, \
    .next = NULL    \
}

#endif
/*drv_led.h*/
#ifndef __DRV_LED_H
#define __DRV_LED_H

void LedDeviceCreate(void);


#endif  /* __DRV_LED_H*/
/*drv_led.c*/
#include "dev_gpio.h"
#include "errno.h"
#include "./drv_config/gpio_config.h"
#include "stm32f4xx_hal.h"

static int LedDrvInit(struct GPIODev *ptdev);
static int LedDrvWrite(struct GPIODev *ptdev,unsigned char status);
static int LedDrvRead(struct GPIODev *ptdev);
    
static GPIODevice gLedDevices[] = {
    D1,D2,D3,D4
};

void LedDeviceCreate(void)
{
    unsigned int num = sizeof(gLedDevices)/sizeof(struct GPIODev);
    for(unsigned int i = 0;i<num;i++)
        IODeviceInsert(&gLedDevices[i]);
}


static int LedDrvInit(struct GPIODev *ptdev)
{
    if(NULL == ptdev)   return -EINVAL;
    
    return ESUCCESS;
}

static int LedDrvWrite(struct GPIODev *ptdev,unsigned char status)
{
    if(NULL == ptdev)   return -EINVAL;
    if(status != 0 && status != 1)  return -EINVAL;
    HAL_GPIO_WritePin(ptdev->port,ptdev->pin,status);
    
    return ESUCCESS;
}

static int LedDrvRead(struct GPIODev *ptdev)
{
    if(NULL == ptdev)   return -EINVAL;
    int status = HAL_GPIO_ReadPin(ptdev->port,ptdev->pin);
    
    return status;
}
 4.3 applications

        app_led.c

#include "dev_gpio.h"
#include "mytype.h"
#include "stm32f4xx_hal.h"

void app_led_test(void)
{
    IODeviceRegister();
    
    GPIODevice *pD1 = IODeviceFind("D1");
    if(NULLDEV == pD1) return;
    GPIODevice *pD2 = IODeviceFind("D2");
    if(NULLDEV == pD2) return;
    GPIODevice *pD3 = IODeviceFind("D3");
    if(NULLDEV == pD3) return;
    GPIODevice *pD4 = IODeviceFind("D4");
    if(NULLDEV == pD4) return;
   
    pD1->Init(pD1);
    pD1->Init(pD2);
    pD1->Init(pD3);
    pD1->Init(pD4);
    while(1)
    {
    pD1->Write(pD1,0);
    HAL_Delay(200);
    pD1->Write(pD1,1);
    HAL_Delay(200);
    }
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值