共2条
1/1 1 跳转至页
我想用C结构描述对象,产品太大。
问
各位老大,我想用C描述对象,产品太大。
结构中定义的函数指针与函数名相同,想作为类的方法用的。
如这样的话,每个对象方法都要一个一个赋值. 答 1: 每个对象方法都要一个一个赋值,有什么问题吗?用C实现OOP的思路是一个好的实践,支持! 答 2: 没法才这样做的,没掌握C++ 答 3: 估计LZ想这样用吧。支持!最好是说成类和实例比较清楚点。类是抽象的概念,实例是具体的存在。
LZ大概是要这样用C吧。支持!
#ifndef IIC_H
#define IIC_H
#include <CommonType.h>
#include <Delay.h>
#define IIC_BITSEQHL 0
#define IIC_BITSEQLH 1
typedef void (*PFNIICSetPin)(BIT btValue);
typedef BIT (*PFNIICGetPin)(void);
typedef struct tagFNIIC
{
BIT btIIC_LL; /*正逻辑或负逻辑*/
BIT btIIC_HH;
INT8U nIICBitSeq;
PFNIICSetPin pfnSetIICSDA;
PFNIICGetPin pfnGetIICSDA;
PFNIICSetPin pfnSetIICSCL;
PFNIICGetPin pfnGetIICSCL;
}FNIIC, *PFNIIC;
/*****************函数声明*****************/
void IICStart(PFNIIC pfnIIC);
void IICStop(PFNIIC pfnIIC);
void IICSendBit(PFNIIC pfnIIC, BIT btValue);
BOOL IICSendAckBit(PFNIIC pfnIIC, BIT btValue);
BOOL IICReceiveAckBit(PFNIIC pfnIIC, BIT btCompare);
INT8U IICReceiveBits8(PFNIIC pfnIIC, INT8U nBitsNumber);
void IICSendBits8(PFNIIC pfnIIC, INT8U nValue, INT8U nBitsNumber);
BYTE IICReceiveByte(PFNIIC pfnIIC);
void IICSendByte(PFNIIC pfnIIC, BYTE byValue);
INT16U IICReceiveBits16(PFNIIC pfnIIC, INT8U nBitsNumber);
void IICSendBits16(PFNIIC pfnIIC, INT16U nValue, INT8U nBitsNumber);
WORD IICReceiveWord(PFNIIC pfnIIC);
void IICSendWord(PFNIIC pfnIIC, WORD wValue);
INT32U IICReceiveBits32(PFNIIC pfnIIC, INT8U nBitsNumber);
void IICSendBits32(PFNIIC pfnIIC, INT32U nValue, INT8U nBitsNumber);
DWORD IICReceiveDWord(PFNIIC pfnIIC);
void IICSendDWord(PFNIIC pfnIIC, DWORD dwValue);
#endif /*IIC_H*/
typedef struct tagAT24CXX
{
INT8U nDeviceAddressBitsCount; /*器件地址位数,包括固定和地址线可选的*/
//INT8U nAddressInDeviceAddressBitsCount; /*地址位在设备地址里的位数*/
INT8U nWordAddressBitsCount; /*地址位数,不包括在设备地址里的地址位数;两部分合起来是真正全部地址*/
INT8U nBytesPerPage; /*每页字节数*/
//INT8U nDeviceAddress;
PFNIIC pfnIIC;
/*************带在函数参数里*********
INT8U nDeviceAddress;
INT8U nAddressInDeviceAddress;
WORD wWordAdress;
*************************************/
}AT24CXX, *PAT24CXX;
#ifndef AT24CXX_H
#define AT24CXX_H
/**********所谓的设备地址nDeviceAddress不包含存储地址,存储地址全部在dwAddress里**********/
/*输入外部设备地址和地址,处理输出命令字设备地址和地址*/
void AT24CXX_MakeAddress(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, PINT8U pnDeviceAddress, PWORD pwAddress);
/**********往总线上送一字节,并收ACK,成功返回1,否则返回0************/
BOOL AT24CXX_SendByte(PAT24CXX pAT24CXXDev, BYTE btData);
BYTE AT24CXX_ReceivedByte(PAT24CXX pAT24CXXDev);
void AT24CXX_Start(PAT24CXX pAT24CXXDev);
void AT24CXX_Stop(PAT24CXX pAT24CXXDev);
BOOL AT24CXX_ByteWrite(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, BYTE btData);
BOOL AT24CXX_PageWrite(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, PBYTE pbtPageData);
BYTE AT24CXX_CurrentRead(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress);
BYTE AT24CXX_RandomtRead(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress);
PBYTE AT24CXX_SeqRead(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, PBYTE pbtData, INT8U nReadNumber);
#endif /*AT24CXX_H*/
/*********测试调用******************/
void Set_IIC_SDA(BIT btValue)
{
//DelayMS(Delay1MS, 1);
btValue &= 0x01;
IIC_SDA_BIT = (BIT)btValue;
}
BIT Get_IIC_SDA(void)
{
//DelayMS(Delay1MS, 1);
return IIC_SDA_BIT&0x01;
}
void Set_IIC_SCL(BIT btValue)
{
//DelayMS(Delay1MS, 1);
btValue &= 0x01;
IIC_SCL_BIT = (BIT)btValue;
}
BIT Get_IIC_SCL(void)
{
//DelayMS(Delay1MS, 1);
return IIC_SCL_BIT&0x01;
}
AT24CXX g_at24cxx = {0};
FNIIC g_fnIIC = {0};
INT8U nData = 0;
WORD i = 0;
BYTE szBuffer[20] = {0};
g_fnIIC.nIICBitSeq = IIC_BITSEQHL;
g_fnIIC.btIIC_LL = 0;
g_fnIIC.btIIC_HH = 1;
g_fnIIC.pfnSetIICSDA = Set_IIC_SDA;
g_fnIIC.pfnGetIICSDA = Get_IIC_SDA;
g_fnIIC.pfnSetIICSCL = Set_IIC_SCL;
g_fnIIC.pfnGetIICSCL = Get_IIC_SCL;
g_at24cxx.nDeviceAddressBitsCount = AT24C08_DEVICE_ADDRESS_BITS_COUNT;
g_at24cxx.nWordAddressBitsCount = AT24C08_WORD_ADDRESS_BITS_COUNT;
g_at24cxx.nBytesPerPage = AT24C08_PAGE_SIZE;
g_at24cxx.pfnIIC = &g_fnIIC;
for (i=0; i<AT24C08_PAGE_SIZE; i++)
{
AT24CXX_ByteWrite(&g_at24cxx, AT24_FIRM_DEVICE_ADDRESS, i, i*2);
//nData = AT24CXX_RandomtRead(&g_at24cxx, AT24_FIRM_DEVICE_ADDRESS, i);
}
答 4: 这种做法可以是固定接口和协议这种做法可以是固定接口和协议,可以评比平台差异,便于移植。以上代码只是做很少修改就移植到51,AVR,ARM上,也就是实现了几个PIN口操作的函数。这种情况下,C++没有优势。不同平台C++的实现可能不一样,C++实现那一块是黑盒,自己管控不了。另外,C++并不是所有的mcu的编译器都支持。我一直在用VC,但在写mcu程序时,还是偏向c,以c++的思想或接口的思想去使用c.除非mcu有N大的ROM和RAM. 答 5: 还可以实现COM接口呢. 创建实例,通过虚表调用.
结构中定义的函数指针与函数名相同,想作为类的方法用的。
如这样的话,每个对象方法都要一个一个赋值. 答 1: 每个对象方法都要一个一个赋值,有什么问题吗?用C实现OOP的思路是一个好的实践,支持! 答 2: 没法才这样做的,没掌握C++ 答 3: 估计LZ想这样用吧。支持!最好是说成类和实例比较清楚点。类是抽象的概念,实例是具体的存在。
LZ大概是要这样用C吧。支持!
#ifndef IIC_H
#define IIC_H
#include <CommonType.h>
#include <Delay.h>
#define IIC_BITSEQHL 0
#define IIC_BITSEQLH 1
typedef void (*PFNIICSetPin)(BIT btValue);
typedef BIT (*PFNIICGetPin)(void);
typedef struct tagFNIIC
{
BIT btIIC_LL; /*正逻辑或负逻辑*/
BIT btIIC_HH;
INT8U nIICBitSeq;
PFNIICSetPin pfnSetIICSDA;
PFNIICGetPin pfnGetIICSDA;
PFNIICSetPin pfnSetIICSCL;
PFNIICGetPin pfnGetIICSCL;
}FNIIC, *PFNIIC;
/*****************函数声明*****************/
void IICStart(PFNIIC pfnIIC);
void IICStop(PFNIIC pfnIIC);
void IICSendBit(PFNIIC pfnIIC, BIT btValue);
BOOL IICSendAckBit(PFNIIC pfnIIC, BIT btValue);
BOOL IICReceiveAckBit(PFNIIC pfnIIC, BIT btCompare);
INT8U IICReceiveBits8(PFNIIC pfnIIC, INT8U nBitsNumber);
void IICSendBits8(PFNIIC pfnIIC, INT8U nValue, INT8U nBitsNumber);
BYTE IICReceiveByte(PFNIIC pfnIIC);
void IICSendByte(PFNIIC pfnIIC, BYTE byValue);
INT16U IICReceiveBits16(PFNIIC pfnIIC, INT8U nBitsNumber);
void IICSendBits16(PFNIIC pfnIIC, INT16U nValue, INT8U nBitsNumber);
WORD IICReceiveWord(PFNIIC pfnIIC);
void IICSendWord(PFNIIC pfnIIC, WORD wValue);
INT32U IICReceiveBits32(PFNIIC pfnIIC, INT8U nBitsNumber);
void IICSendBits32(PFNIIC pfnIIC, INT32U nValue, INT8U nBitsNumber);
DWORD IICReceiveDWord(PFNIIC pfnIIC);
void IICSendDWord(PFNIIC pfnIIC, DWORD dwValue);
#endif /*IIC_H*/
typedef struct tagAT24CXX
{
INT8U nDeviceAddressBitsCount; /*器件地址位数,包括固定和地址线可选的*/
//INT8U nAddressInDeviceAddressBitsCount; /*地址位在设备地址里的位数*/
INT8U nWordAddressBitsCount; /*地址位数,不包括在设备地址里的地址位数;两部分合起来是真正全部地址*/
INT8U nBytesPerPage; /*每页字节数*/
//INT8U nDeviceAddress;
PFNIIC pfnIIC;
/*************带在函数参数里*********
INT8U nDeviceAddress;
INT8U nAddressInDeviceAddress;
WORD wWordAdress;
*************************************/
}AT24CXX, *PAT24CXX;
#ifndef AT24CXX_H
#define AT24CXX_H
/**********所谓的设备地址nDeviceAddress不包含存储地址,存储地址全部在dwAddress里**********/
/*输入外部设备地址和地址,处理输出命令字设备地址和地址*/
void AT24CXX_MakeAddress(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, PINT8U pnDeviceAddress, PWORD pwAddress);
/**********往总线上送一字节,并收ACK,成功返回1,否则返回0************/
BOOL AT24CXX_SendByte(PAT24CXX pAT24CXXDev, BYTE btData);
BYTE AT24CXX_ReceivedByte(PAT24CXX pAT24CXXDev);
void AT24CXX_Start(PAT24CXX pAT24CXXDev);
void AT24CXX_Stop(PAT24CXX pAT24CXXDev);
BOOL AT24CXX_ByteWrite(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, BYTE btData);
BOOL AT24CXX_PageWrite(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, PBYTE pbtPageData);
BYTE AT24CXX_CurrentRead(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress);
BYTE AT24CXX_RandomtRead(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress);
PBYTE AT24CXX_SeqRead(PAT24CXX pAT24CXXDev, INT8U nDeviceAddress, DWORD dwAddress, PBYTE pbtData, INT8U nReadNumber);
#endif /*AT24CXX_H*/
/*********测试调用******************/
void Set_IIC_SDA(BIT btValue)
{
//DelayMS(Delay1MS, 1);
btValue &= 0x01;
IIC_SDA_BIT = (BIT)btValue;
}
BIT Get_IIC_SDA(void)
{
//DelayMS(Delay1MS, 1);
return IIC_SDA_BIT&0x01;
}
void Set_IIC_SCL(BIT btValue)
{
//DelayMS(Delay1MS, 1);
btValue &= 0x01;
IIC_SCL_BIT = (BIT)btValue;
}
BIT Get_IIC_SCL(void)
{
//DelayMS(Delay1MS, 1);
return IIC_SCL_BIT&0x01;
}
AT24CXX g_at24cxx = {0};
FNIIC g_fnIIC = {0};
INT8U nData = 0;
WORD i = 0;
BYTE szBuffer[20] = {0};
g_fnIIC.nIICBitSeq = IIC_BITSEQHL;
g_fnIIC.btIIC_LL = 0;
g_fnIIC.btIIC_HH = 1;
g_fnIIC.pfnSetIICSDA = Set_IIC_SDA;
g_fnIIC.pfnGetIICSDA = Get_IIC_SDA;
g_fnIIC.pfnSetIICSCL = Set_IIC_SCL;
g_fnIIC.pfnGetIICSCL = Get_IIC_SCL;
g_at24cxx.nDeviceAddressBitsCount = AT24C08_DEVICE_ADDRESS_BITS_COUNT;
g_at24cxx.nWordAddressBitsCount = AT24C08_WORD_ADDRESS_BITS_COUNT;
g_at24cxx.nBytesPerPage = AT24C08_PAGE_SIZE;
g_at24cxx.pfnIIC = &g_fnIIC;
for (i=0; i<AT24C08_PAGE_SIZE; i++)
{
AT24CXX_ByteWrite(&g_at24cxx, AT24_FIRM_DEVICE_ADDRESS, i, i*2);
//nData = AT24CXX_RandomtRead(&g_at24cxx, AT24_FIRM_DEVICE_ADDRESS, i);
}
答 4: 这种做法可以是固定接口和协议这种做法可以是固定接口和协议,可以评比平台差异,便于移植。以上代码只是做很少修改就移植到51,AVR,ARM上,也就是实现了几个PIN口操作的函数。这种情况下,C++没有优势。不同平台C++的实现可能不一样,C++实现那一块是黑盒,自己管控不了。另外,C++并不是所有的mcu的编译器都支持。我一直在用VC,但在写mcu程序时,还是偏向c,以c++的思想或接口的思想去使用c.除非mcu有N大的ROM和RAM. 答 5: 还可以实现COM接口呢. 创建实例,通过虚表调用.
共2条
1/1 1 跳转至页
回复
有奖活动 | |
---|---|
【有奖活动】分享技术经验,兑换京东卡 | |
话不多说,快进群! | |
请大声喊出:我要开发板! | |
【有奖活动】EEPW网站征稿正在进行时,欢迎踊跃投稿啦 | |
奖!发布技术笔记,技术评测贴换取您心仪的礼品 | |
打赏了!打赏了!打赏了! |
打赏帖 | |
---|---|
【笔记】生成报错synthdesignERROR被打赏50分 | |
【STM32H7S78-DK评测】LTDC+DMA2D驱动RGBLCD屏幕被打赏50分 | |
【STM32H7S78-DK评测】Coremark基准测试被打赏50分 | |
【STM32H7S78-DK评测】浮点数计算性能测试被打赏50分 | |
【STM32H7S78-DK评测】Execute in place(XIP)模式学习笔记被打赏50分 | |
每周了解几个硬件知识+buckboost电路(五)被打赏10分 | |
【换取逻辑分析仪】RA8 PMU 模块功能寄存器功能说明被打赏20分 | |
野火启明6M5适配SPI被打赏20分 | |
NUCLEO-U083RC学习历程2-串口输出测试被打赏20分 | |
【笔记】STM32CUBEIDE的Noruletomaketarget编译问题被打赏50分 |