• C++设计模式---Strategy模式


    一、前言

      学习的第一个设计模式!不知道理解的对不对,期望大家一起多交流~

      Strategy模式:策略模式,定义了算法族,分别封装起来,此模式可以让算法的变化独立于使用算法的客户。Strategy模式将逻辑算法封装到一个类中,通过组合的方式将具体的算法实现在组合对象中,再通过委托的方式将抽象的接口的实现委托给组合对象实现。其模型结构图如下:

     二、Strategy策略实例

      最近在写遥感影像融合相关算法,PCA、Brovey和SFIM算法,正好可以用于这次学习Strategy策略。

      关于这三个融合算法都属于替换类算法,大概思路就是用一个替换另外一个。然后获得高分辨的高频信息和地分辨的光谱信息。

      依据Strategy策略的思想,我们首先定义一个CContextFusion类,里面有一个DoFusionAction()方法,主要用于实现算法逻辑抽象接口,其头文件如下:

    #pragma once
    #include "StrategyFusion.h"
    
    class CStrategyFusion;
    
    class CContextFusion
    {
    public:
    	CContextFusion(CStrategyFusion *stg);
    	~CContextFusion(void);
    
    	bool DoFusionAction();
    
    private:
    	CStrategyFusion *m_stg;
    };
    

      cpp文件如下:

    #include "ContextFusion.h"
    
    CContextFusion::CContextFusion( CStrategyFusion *stg )
    {
    	m_stg = stg;
    }
    CContextFusion::~CContextFusion(void)
    {
    	if(!m_stg)
    		delete m_stg;
    }
    
    bool CContextFusion::DoFusionAction()
    {
    	return m_stg->runFusion();
    }
    

      

    完成这个类后,我们首先定义一个融合算法超类CStrategyFusion,考虑到以上三种算法都要实现影像的重采样和增益系数的计算。为此,我们把这两个方法的实现放在超类中,对于其他与融合算法相关的方法,放到具体的算法类中。其类结构关系如下所示:

    头文件分别如下:

    #pragma once
    #include <iostream>
    #include <string>
    #include <omp.h>
    #include <gdal_alg_priv.h>
    
    
    class CStrategyFusion
    {
    public:
    	CStrategyFusion(void);
    	virtual ~CStrategyFusion(void);
    	virtual bool runFusion() = 0;
    
    protected:
    	int ReSampleMSSToPAN();
    	void getGAIN();
    
    	std::string m_panFileName;
    	std::string m_mssFileName;
    	std::string m_resampleFileName;
    	std::string m_FusionFileName;
    	GDALDataType m_dt;
    	int m_resampleModel;
    
    	int m_gainX;  // X方向增益像元个数
    	int m_gainY;  // Y方向增益像元个数
    	int m_FusionWidth;  // 融合后影像宽
    	int m_FusionHeight; // 融合后影像高
    	double m_FusionGeoTransform[6];
    
    //private:
    
    };
    

      

    #pragma once
    #include "strategyfusion.h"
    
    class CStrategyFusionByPCA :
    	public CStrategyFusion
    {
    public:
    	CStrategyFusionByPCA(void);
    	~CStrategyFusionByPCA(void);
    
    	bool runFusion();
    
    private:
    	double *calMSSMean();
    	double *calCovMaxtrix(double *bandMean);
    	bool eejcb(double a[],int n,double v[],double eps,int jt);
    	void sortEigenVector( int iBandCount,double * eigenVector,double * covAfterEejcb);
    	void PCATransform(double *eigenVector);
    	double* cdf(int *h,int length);
    	void matchHistogram();
    	void inverseMatrix( double *matrix, int n );
    	void invertPCA(double * eigenVector);
    
    	std::string m_PCAFileName;
    	std::string m_PanNewFileName;
    };
    

      

    #pragma once
    #include "strategyfusion.h"
    
    class CStrategyFusionByBrovey :
    	public CStrategyFusion
    {
    public:
    	CStrategyFusionByBrovey(void);
    	~CStrategyFusionByBrovey(void);
    
    	bool runFusion();
    
    private:
    	bool CNByBrovery();
    };
    

      

    #pragma once
    #include "strategyfusion.h"
    
    class CStrategyFusionBySFIM :
    	public CStrategyFusion
    {
    public:
    	CStrategyFusionBySFIM(void);
    	~CStrategyFusionBySFIM(void);
    
    	bool runFusion();
    
    private:
    	bool FilterMeanByPan();
    	bool SFIM();
    };
    

      

    总结:通过Strategy策略,我们可以自由、方便的补充新的基于替换类的融合算法,甚至其他所有的融合算法,换句话说就是可以自由定制自己的融合算法类,这种基于接口的实现不会因为继承而导致不可预计的危险。

  • 相关阅读:
    jvm 垃圾收集器
    MySQL 查询结果去除边框
    MySQL5.7 半同步复制技术
    MySQL 5.7半同步复制技术 zero
    redis 迁移工具 redisshake
    MySQL 如何找出占用CPU较高的SQL
    部署redis sentinel
    MySQL的SQL_CALC_FOUND_ROWS 类似count(*)
    MongoDB 副本集删除超级用户后恢复
    【Linux】关于 Systemd/Journal
  • 原文地址:https://www.cnblogs.com/zyore2013/p/5819698.html
Copyright © 2020-2023  润新知