c++ 笔记二

1.可变参数和限制输入:

代码:不限制输入,返回+的总和

#include <iostream>
#include <filesystem>
#include <string>
#include <vector>

template<class Type>
concept AddAble = requires(Type T1, Type T2) {
	{T1 + T2 }->std::convertible_to<Type>;
};

template< AddAble... Args>
void Add(Args... arge) {
	using argeType = std::common_type_t<Args...>;
	argeType number  = (arge + ...);
	std::cout << " number is >>>" << number;
}
int main() {
	Add(123,788,888);
	Add(std::string {"dsafdf"},std::string{"ddddd"});
	return 0;
}

详解:

自动推断类型的方法:

在C++中,可以使用多种工具和特性来推断一个参数的类型。以下是一些常用的方法和工具:

auto 关键字: auto 关键字可以用于变量声明中,以自动推断类型。

auto x = 42;       // 推断 x 的类型为 int
auto y = 3.14;     // 推断 y 的类型为 double
auto z = x + y;    // 推断 z 的类型为 double

decltype 关键字: decltype 可以用于获取表达式的类型,而不实际计算该表达式。

int x = 42;
decltype(x) y = 43; // y 的类型是 int

函数模板和模板参数推断: 在函数模板中,参数类型可以自动推断。

template<typename T>
void printType(T t) {
    std::cout << "Type is: " << typeid(t).name() << std::endl;
}

int main() {
    printType(42);     // T 被推断为 int
    printType(3.14);   // T 被推断为 double
    return 0;
}

std::common_type: 用于推断多个类型的公共类型。

std::common_type_t<int, double> result; // result 的类型是 double

std::invoke_result: 用于推断函数调用返回的类型。

int func(double);
using ResultType = std::invoke_result_t<decltype(func), double>; // ResultType 是 int

 C++20 Concepts: 概念可以用于约束模板参数,并能更清晰地表达类型要求。

template<typename T>
concept Addable = requires(T a, T b) {
    { a + b } -> std::convertible_to<T>;
};

template<Addable T>
void add(T a, T b) {
    std::cout << a + b << std::endl;
}

 std::remove_referencestd::remove_cv: 用于在模板元编程中获取类型的基本形式。

template<typename T>
void func(T&& param) {
    using Type = std::remove_reference_t<T>;
    // Type 是去除了引用的类型
}

std::common_with 和std::convertible_to在限制模版中经常使用,我们看一下他们的区别:

std::common_withstd::convertible_to 是C++20中引入的概念,用于约束模板参数类型。尽管它们看似相似,但它们的用途和语义有所不同。

std::common_with

std::common_with 概念用于检查两个类型是否有一个公共类型,即可以相互转换为一个共同的类型。具体来说,std::common_with<T, U> 检查以下条件:

  1. std::common_type_t<T, U> 存在。
  2. std::common_type_t<U, T> 存在。
  3. std::common_type_t<T, U>std::common_type_t<U, T> 是同一个类型。
  4. TU 都可以转换为 std::common_type_t<T, U>

简而言之,std::common_with 确保两个类型可以相互转换,并且这种转换是对称且一致的。

std::convertible_to

std::convertible_to 概念用于检查一个类型是否可以隐式转换为另一个类型。具体来说,std::convertible_to<T, U> 检查以下条件:

  1. std::is_convertible_v<T, U>true
  2. static_cast<U>(std::declval<T>()) 是一个有效的表达式,并且其结果可以被转换为 U

简而言之,std::convertible_to 确保一个类型可以隐式转换为另一个类型。

代码示例:

class Base
{
public:
	void Test() { };
};

class Son:public Base
{
public:
	void printf() {
		std::cout << " -------------------------------- ";
	};
};

class TestClass
{
public:
	void test() { }
};

template<class T1,class T2>
requires std::convertible_to<T1,T2>
    void FuncConver(T1 arg1,T2 arg2) {

	}
template <class T1,class T2>
requires std::common_with<T1,T2>
void FuncTest(T1 agr1,T2 agr2) {
	agr2.printf();
}
int main() {
	Base ba;
	Son so;
	TestClass test {};
	FuncTest(ba,so);
	FuncConver(1,3434);
	// FuncConver(ba,so);
//	Add(123,788,888);
//	Add(std::string {"dsafdf"},std::string{"ddddd"});
	return 0;
}

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值