平行世界用c++模板代替继承和包含关系

Posted qianbo_insist

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了平行世界用c++模板代替继承和包含关系相关的知识,希望对你有一定的参考价值。

现实

现实的c++程序挺让人无奈的,很多人喜欢重构,重写,没有积蓄,原因是新的方法和新的class 等等不断填充代码,这一点其实确实不如像java, go ,node 一样。

c++ 依然在于他的高效,其发展也很快,是一个良好的工具。

比如我们写了一个Path 类

struct Path 

	Path() 
	explicit Path(const char* path) 
		strncpy_s(m_path, path,1024);
	
	int getHash() const  return m_hash; 
	const char* c_str() const  return m_path; 
	bool isEmpty() const  return m_path[0] == '\\0'; 

private:
	char m_path[1024] = 0;
	int m_hash = 10000000;
;

后面需求增加,变动,我们增加了hash类

struct Hash_ra

	static int hash_rotate(const char* key, int prime)
	
		int hash, i;
		int len = strlen(key);
		for (hash = len, i = 0; i < len; i++)
		
			hash = (hash << 4 >> 28) ^ key[i];
			return (hash % prime);
		
		return 0;
	
	
	static int hash_add(const char* key, int prime)
	

		int hash, i;
		int len = strlen(key);
		for (hash = len, i = 0; i < len; i++)
			hash += key[i];
		return (hash % prime);
	
	// 求核数后面最大的素数
		//只能被自己和1整除的数为素数

		static int hash_next_prime(int num) 
		if (num == 1)
			return 2;
		if (num == 2)
			return 3;
		if (num % 2 == 0)
			++num;
		int i;
		bool flag = false;
		while (1)
		
			flag = false;
			for (i = 3; i < num; i += 2)
				if (num % i == 0) 
					flag = true;
					break;
				
			if (!flag)
				return num;
			num += 2;
		
	

;

这时候麻烦的事情来了,我们要组合的时候,是包含还是继承,重新封装还是新建类作为两个类的包含者,方法很多,写的时候可能会经常改。

我们可以使用模板来作为平行世界的调剂,以下是示例:

template <typename Key> struct HashFunc;
template<>
struct HashFunc<Path>

	static uint32_t get(const Path& key)
	
		uint32_t s = 0;
		const char* str = key.c_str();
		for (int i = 0; i < strlen(str); i++)
			s += *(str + i);
		const int hash = key.getHash();
		return s+hash;
	
;

可以看出,没有继承和包含等等关系,我们在使用的时候比较清楚,是平行的

    //其他地方的定义p
    Path p("/root/home/qianbo/test");
    //使用过程中需要hash函数
	uint32_t ret = HashFunc<Path>::get(p);
	std::cout << "hash is " << ret << std::endl;

要把Path 和 Hash_ra 两个类一起使用,当然,我们完全可以不使用模板,不过,使用模板是有扩展的好处的,对于结合和各种类以及清晰地展现我们的目的,模板是有很好的延展,熟练使用就知道了。

template<>
struct HashFunc<Hash_ra>

	static int hash_add_get(Path p)
	
		return Hash_ra::hash_add(p.c_str(),1001);
	
	static int hash_rotate_get(Path p, int prime)
	
		int ret = Hash_ra::hash_rotate(p.c_str(), prime);
		return ret;
	
;

下面增加一个普通方式,以来显示可以整合各个类和方法

template <typename Key> struct HashFunc

	int get(Key key)
	
		/// <summary>
		/// 其他修改
		
		return 10001+key.get();
	
;

struct Path2

	int get()
	
		return 1000;
	
;

使用

下面使用模板来计算

int main()

	Path p("/root/home/qianbo/test");
	uint32_t ret = HashFunc<Path>::get(p);
	std::cout << "hash is " << ret << std::endl;

	int ret2 = HashFunc<Hash_ra>::hash_add_get(p);

	std::cout << "hash is "<< ret2 << std::endl;

	int ret3 = HashFunc<Hash_ra>::hash_rotate_get(p,1001);
	std::cout << "hash is " << ret3 << std::endl;


	Path2 a;
	HashFunc<Path2> b;
	std::cout<<b.get(a)<<std::endl;

	std::hash<int> hash_int;// Function object to hash int
	std::vector<int> n -5, -2, 2, 5, 10 ;
	std::transform(std::begin(n), std::end(n), std::ostream_iterator<size_t>(std::cout, " "), hash_int);
	return 0;

下面是展示

以上是关于平行世界用c++模板代替继承和包含关系的主要内容,如果未能解决你的问题,请参考以下文章

C# 中的 C++ 模板继承等价物是啥?

C++模板类和类模板

在 C++ 中的多个类中使用模板类

顶层父类的构建

c++程序中,iostream可以被fstream代替吗

C++ 隐藏继承层次结构中的成员函数,紧盯 CRTP