您的位置:首页 > 编程语言 > C语言/C++

C++学习笔记:c++模型设计和实现 经典案例

2016-02-27 22:17 573 查看
信息系统框架 集成 第三方产品 案例 (socket传送接收,以及加解密过程)

案例背景:一般的企业信息系统都有成熟的框架。软件架构一般不发生变化,能自由的集成第三方厂商的产品。

案例要求:请你在企业信息系统框架中集成第三方厂商的Socket通信产品和第三方厂商加密产品。

第三方厂商的socket通信产品:完成两点之间的通信;

第三方厂商加密产品:完成数据发送时加密;数据解密时解密。

案例要求:1)能支持多个厂商的Socket通信产品入围

2)能支持多个第三方厂商加密产品的入围

3)企业信息系统框架不轻易发生框架

需求实现:思考1:企业信息系统框架、第三方产品如何分层 (通过接口层)

思考2:企业信息系统框架,如何自由集成第三方产品 (软件设计:模块要求松,接口要求紧)

思考3:软件分层以后,开发企业信息系统框架的程序员,应该做什么?

第三方产品入围应该做什么?

编码实现:

分析有多少个类。首先 编写CSocketProtocol 信息系统抽象类,提供其他厂商的接口

CSckFactoryImp1 第一个厂商 CSckFactoryImp2 第二个厂商...

CEncDesProtocol 加密类 ciscoEncdes解密类

1.定义CScoketProtocol.h 抽象类

#pragma once
#include "stdafx.h"
#include <iostream>
using namespace std;
class CSocketProtocol{
public:
//客户端初始化 获取handle上下
virtual int cltSocketInit() = 0;
virtual int cltSocketSend(unsigned char *buf, int buflen) = 0;
virtual int cltSocketRev(unsigned char *buf, int *buflen) = 0;
virtual int cltSocketDestroy()=0;
};


2.编写框架函数

//面向对象类编程,框架实现完毕
int SckSendAndRec(CSocketProtocol *sp,unsigned char *in,int inlen,unsigned char *out,int *outlen){
int ret = 0;
if (ret != 0){
goto End;
}
ret = sp->cltSocketInit();
if (ret != 0){
goto End;
}
ret = sp->cltSocketSend(in,inlen);
if (ret != 0){
goto End;
}
ret = sp->cltSocketRev(out,outlen);
if (ret != 0){
goto End;
}
End:
ret = sp->cltSocketDestroy();
return 0;
}


3.编写框架测试函数 也就是我们通常写的小程序里的main(),这是业务层,经常会变动。

//测试  上层业务(经常会变)
int _tmain(int argc, _TCHAR* argv[])
{
int ret;
unsigned char in[4096];
int inlen=0;
unsigned char out[4096];
int outlen = 0;
strcpy((char *)in, "adcadadwa");
inlen = 9;

CSocketProtocol *sp = NULL;
sp = new CSckFactory;//第三个厂商 父类指针指向子类对象
//sp = new CSckFactory02...添加若干个厂商都可以

ret = SckSendAndRec(sp,in,inlen,out,&outlen);
if (ret != 0){
printf("func SckSendAndRec() err:%d\n", ret);
return ret;
}
delete sp;//想通过父类指针释放左右的子类对象的资源

return 0;
}


4.厂商1(CSckFactory) 实现CScoketProtol.....(厂商2等同)

CSckFactorh.h

#include <iostream>
using namespace std;
#include "CSocketProtocol.h"

class CSckFactory:public CSocketProtocol{
public:
virtual int cltSocketInit();//客户端初始化
virtual int cltSocketSend(unsigned char *buf, int buflen);//客户端发报文
virtual int cltSocketRev(unsigned char *buf, int *buflen);//客户端收报文
virtual int cltSocketDestroy();//客户端释放资源
private:
unsigned char *p;
int len;
};


CSckFactorh.cpp

#include"stdafx.h"
#include"CSckFactory.h"
#pragma warning(disable:4996)
int CSckFactory::cltSocketInit(){
p = NULL;
len = 0;
return 0;
}
int  CSckFactory::cltSocketSend(unsigned char *buf, int buflen){
p = (unsigned char *)malloc(sizeof(unsigned char) * buflen);
if (p == NULL){
return -1;
}
memcpy(p,buf,buflen);

len = buflen;
return 0;
}
int  CSckFactory::cltSocketRev(unsigned char *buf, int *buflen){
if (buf == NULL || buflen == NULL){
return -1;
}
*buflen=this->len;
memcpy(buf,this->p,this->len);
return 0;
}
int  CSckFactory::cltSocketDestroy(){
if (p != NULL){
free(p);
p = NULL;
}
return 0;
}


5.抽象加密接口(CEncDesProtocol),加密厂商1(CHwImp),加密厂商2(CCiscoImp),集成实现业务模型

5.1 定义 加解密 抽象类 CEndDesProtocol.h

#pragma once
class CEnsDesProtocol{
public://加解密的接口
CEnsDesProtocol(){

}
virtual ~CEnsDesProtocol(){

}
virtual int EncData(unsigned char *plain,int plainlen,unsigned char *cryptdata,
int *cryptlen)=0;
virtual int DecData(unsigned char *cryptdata, int cryptlen, unsigned char *plain,
int *plainlen) = 0;
};


5.2 定义加密厂商1 CHwImp类 继承加解密抽象类

HwEncDec.h



#include<iostream>
using namespace std;

#include "CEndDesProtocol.h"

class HwEncDec :public CEnsDesProtocol{
virtual int EncData(unsigned char *plain, int plainlen, unsigned char *cryptdata,
int *cryptlen);
virtual int DecData(unsigned char *cryptdata, int cryptlen, unsigned char *plain,
int *plainlen);
};


HwEncDec.cpp

#include"stdafx.h"
#include<iostream>
using namespace std;

#include "HwEncDec.h"
#include"des.h"

int HwEncDec::EncData(unsigned char *plain, int plainlen, unsigned char *cryptdata,
int *cryptlen){
int ret = 0;
//用户使用的函数
ret=DesEnc(
plain,
plainlen,
cryptdata,
cryptlen);
if (ret != 0){
printf("func DesEnc() err:%d\n",ret);
return ret;
}
return ret;
};

//用户使用函数des解密

int HwEncDec::DecData(unsigned char *cryptdata, int cryptlen, unsigned char *plain,
int *plainlen){
int ret=DesDec(
cryptdata,
cryptlen,
plain,
plainlen);
if (ret != 0){
printf("func DesEnc() err:%d\n",ret);
return ret;
}
return ret;
};


5.3 框架函数(继承了加解密,较之前进行的升级)

//面向对象类编程,框架实现完毕
int SckSendAndRec_EncDec(CSocketProtocol *sp, CEnsDesProtocol *ed, unsigned char *in, int inlen, unsigned char *out, int *outlen){
int ret = 0;
ret = sp->cltSocketInit();
if (ret != 0){
goto End;
}

unsigned char data[4096];
int datalen = 0;
ret = ed->EncData(in,inlen,data,&datalen);

//发送数据之前对数据加密
ret = sp->cltSocketSend(data,datalen);

if (ret != 0){
goto End;
}

ret = sp->cltSocketRev(data, &datalen);//收到的数据是密文,需要进行解密
ret = ed->DecData(data,datalen,out,outlen);
if (ret != 0){
goto End;
}
End:
ret = sp->cltSocketDestroy();
return 0;
}


5.4 测试函数(较之前增加一个加解密的接口 new了一个华为厂商的对象)

//测试  上层业务(经常会变)
int main()
{
int ret;
unsigned char in[4096];
int inlen=0;
unsigned char out[4096];
int outlen = 0;
strcpy((char *)in, "adcadadwa");
inlen = 9;

CSocketProtocol *sp = NULL;
sp = new CSckFactory;//第三个厂商 父类指针指向子类对象
//sp = new CSckFactory02...添加若干个厂商都可以

//定义一个加解密的接口
CEnsDesProtocol *ed = NULL;
ed = new HwEncDec;//华为使用加解密

ret = SckSendAndRec_EncDec(sp, ed, in, inlen, out, &outlen);
if (ret != 0){
printf("func SckSendAndRec() err:%d\n", ret);
return ret;
}
delete sp;//想通过父类指针释放左右的子类对象的资源
delete ed;
return 0;
}


6.框架(c语言函数方式,框架函数;C++类方式,框架类)

我们把框架函数改成面向对象框架 即 框架类

class MainOp{//组合两个抽象类属性
public:
MainOp(){
this->sp = NULL;
this->ed = NULL;
}
MainOp(CSocketProtocol *sp,CEnsDesProtocol *ed){
this->sp = sp;
this->ed = ed;
}
//留一个接口,有机会让别人塞进来,这就是注入
void setSp(CSocketProtocol *sp){
this->sp = sp;
}
void setEd(CEnsDesProtocol *ed){
this->ed = ed;
}
public://业务框架
int SckSendAndRec_EncDec(unsigned char *in, int inlen, unsigned char *out, int *outlen){
int ret = 0;
ret = this->sp->cltSocketInit();
if (ret != 0){
goto End;
}

unsigned char data[4096];
int datalen = 0;
ret = this->ed->EncData(in, inlen, data, &datalen);

//发送数据之前对数据加密
ret = this->sp->cltSocketSend(data, datalen);

if (ret != 0){
goto End;
}
ret = this->sp->cltSocketRev(data, &datalen);//收到的数据是密文,需要进行解密
ret = this->ed->DecData(data, datalen, out, outlen);
if (ret != 0){
goto End;
}
End:
ret = this->sp->cltSocketDestroy();
return 0;
}
private:
CSocketProtocol *sp;
CEnsDesProtocol *ed;
};
再更改业务测试代码,如下:

//测试  上层业务(经常会变)
int main()
{
int ret=0;
unsigned char in[4096];
int inlen=0;
unsigned char out[4096];
int outlen = 0;
strcpy((char *)in, "adcadadwa");
inlen = 9;

CSocketProtocol *sp = NULL;
sp = new CSckFactory;//第三个厂商 父类指针指向子类对象
//sp = new CSckFactory02...添加若干个厂商都可以

//定义一个加解密的接口
CEnsDesProtocol *ed = NULL;
ed = new HwEncDec;//华为使用加解密

//集成框架变成类模式
MainOp *myMainOp = new MainOp;
myMainOp->setEd(ed);
myMainOp->setSp(sp);
ret=myMainOp->SckSendAndRec_EncDec(in,inlen,out,&outlen);

//ret = SckSendAndRec_EncDec(sp, ed, in, inlen, out, &outlen);
if (ret != 0){
printf("func SckSendAndRec() err:%d\n", ret);
return ret;
}
delete sp;//想通过父类指针释放左右的子类对象的资源
delete ed;
delete myMainOp;
return 0;
}


MVC:

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: