当前位置:   article > 正文

在c++ 20下使用微软的proxy库替代传统的virtual动态多态

在c++ 20下使用微软的proxy库替代传统的virtual动态多态
传统的virtual动态多态,经常会有下面这样的使用需求:
#include <iostream>
#include <vector>

// 声明一个包含virtual虚函数的基类
struct shape
{
	virtual ~shape() {}

	virtual void draw() = 0;
};

// 派生,实现virtual虚函数
struct rectangle : shape
{
	virtual void draw() override
	{
		std::cout << "rectangle" << std::endl;
	}
};

// 派生,实现virtual虚函数
struct circle : shape
{
	virtual void draw() override
	{
		std::cout << "circle" << std::endl;
	}
};

int main()
{
	// 由于要用vector容器来保存各种不同的对象,所以这里容器元素的类型只能使用基类指针
	std::vector<shape*> vec;

	vec.emplace_back(new rectangle());
	vec.emplace_back(new circle());

	// 通过virtual动态多态调用,来实现调用真正的对象类型的成员函数
	for (const auto& p : vec)
	{
		p->draw();
	}

	// 输出:
	// rectangle
	// circle
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
上面同样的需求,换成proxy库来实现是这样的:
#include <iostream>
#include <vector>
#include "proxy.h"

// 声明一个代理类,最终会通过这个代理类去调用真正的类对象的成员函数
struct draw : pro::dispatch<void()>
{
	template <class T>
	void operator()(T& self) { self.draw(); }
};

struct shape : pro::facade<draw> {};

// 不需要派生,不需要virtual虚函数
struct rectangle
{
    void draw()
    {
        std::cout << "rectangle"<< std::endl;
    }
};

// 不需要派生,不需要virtual虚函数
struct circle
{
    void draw()
    {
        std::cout << "circle" << std::endl;
    }
};

int main()
{
    // 这里容器元素的类型是个proxy的代理类型
    std::vector<pro::proxy<shape>> shapes;

	shapes.emplace_back(pro::make_proxy<shape>(rectangle()));
	shapes.emplace_back(pro::make_proxy<shape>(circle()));

    // 注意这里的调用方式和virtual动态多态的调用方式不同
    for (auto& p : shapes)
    {
        p.invoke<draw>();
    }

    // 输出:
    // rectangle
    // circle
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49

可以看到,换成proxy库之后,不再有virtual虚函数,而且是非侵入式的,我觉得这种方式非常棒,很优雅。至于性能测试,我没有去做。

详情见这个开源仓库地址:https://github.com/microsoft/proxy

最后编辑于:2023-08-24
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/2023面试高手/article/detail/141750
推荐阅读
相关标签
  

闽ICP备14008679号