这段代码是一个 C++ 的类模板,定义了若干个类型特征 trait,用于在编译期判断某个类型是否满足特定的条件。其中包括函数可调用性、是否为输入范围(input range)、是否有 size() 成员等特征。这些 trait 可以被用于 SFINAE 技术,实现模板函数的重载和替代选择。

SFINAE 是 C++ 中的一种编译期技术,其全称为 Substitution Failure Is Not An Error。大致意思是在实例化一个模板时,如果某个候选函数无法通过编译(即出现了 substitution failure),则该函数不会被选择,而是去选择其他可行的候选函数。这样可以在编译期根据条件选择不同的实现方式。

常用的 SFINAE 技巧包括使用 enable_if、decltype 和 decltype() 等语句,在模板参数设计和选择函数重载等方面都有广泛应用,是 C++ 代码中一种常用的元编程方法。

enable_if

C++ enable_if的使用_c++. enable_if_jeffasd的博客-CSDN博客

理解 std::declval 和 decltype - 掘金 (juejin.cn)

emun

emun class

init

Type a Type a(xxx) Type a{xxx}

Type a = a Type a = {xxx} Type a = a(xxx)

new

https://blog.csdn.net/xiaorenwuzyh/article/details/44514815

default/delete

struct A{ A() = delete; int t(){ return 1; } } struct A{A()=defaule;}

constexpr

constexpr (C++) | Microsoft Learn

auto

auto (C++) | Microsoft Learn

decltype

自动推导类型

decltype(exp) decltype(a, b,c…)

delctype(a,b) 一个C++中的表达式,称为“逗号运算符”。它先对表达式a求值,然后对表达式b求值,并返回b的结果。同时,它会根据a和b的类型进行类型推断并返回表达式整体的类型。例如,如果a是int类型,而b是double类型,则decltype(a,b)将返回double类型。

std::declval

typid()

std::type_info

using

类似 typedef

后置返回值类型(trailing return type)

看一个例子

 
template<typename R ,typename T,typename Y>
R add(T v1, Y v2)
{
    return v1+v2;
}

使用 decltype 自动推导 v1 + v2, 可以省去一个变量

template<typename T, typename Y>
decltype(v1+v2) add(T v1, Y v2) {
	return v1+v2;
}

由于执行 decltype 时 v1, v2 未定义, 会报错。使用 trailing return type 来解决这个问题.

template<typename T, typename Y>
auto add(T v1, Y v2)->decltype(v1+v2){
	return v1+v2;
}

std::initializer_list

只要是 {1,2,3} 类似, 用花括号包裹起来的都会自动解析成 std::initializer 类型

运算符重载

不仅类可以重载运算符, 也可以在 namespace 里边重载运算符

//Test.h
#pragma once
#include <iostream>
#include <string>
 
using namespace std;
 
namespace test {
	class _a {
	public:
		_a(std::string var) :_var(var) {}
		std::string toString() {
			return this->_var;
		}
	private:
		std::string _var;
	};
 
	class _b {
	public:
		_b(int var) :_var(var) {}
		std::string toString() {
			return std::to_string(this->_var);
		}
 
		int value() {
			return this->_var;
		}
	private:
		int _var;
	};
 
	_b o(int var) {
		return _b{ var };
	}
 
	_a o(std::string var) {
		return _a{ var };
	}
	class Test {
	
	public:
		
		Test(_a a, _b b):A(a), B(b) {}
 
		void info() {
			cout << this->A.toString() << this->B.toString()<< endl;
		}
 
		~Test() {};
 
	private:
		_a A;
		_b B;
	};
 
	Test operator ,(_a a, _b b) {
		return Test{ a,b };
	}
 
	_a operator & (_a a1, _a a2) {
		std::string t = a1.toString() + a2.toString();
		return _a{ t };
	}
 
	_b operator |(_b b1, _b b2) {
		return _b{ b1.value() + b2.value() };
	}
 
}
 

重载 , &, | 可以实现特殊语法

//main.cpp
 
#include <iostream>
#include "Test.h"
 
using namespace std;
 
int main() {
	auto t = (
		_a{"tom"}&o("jack"),
		_b{4}|o(5)
	);
 
 
	t.info();
	return 0;
}

cast

C++四种类型强制转换——const_cast、static_cast、dynamic_cast、reinterpret_cast_孟小胖_H的博客-CSDN博客

重载bool()

class A
{
public:
    explicit operator bool()const noexcept { return false; }
};
 
int main()
{
    A a;
    if (a); //如果不重载bool()此处编译器会报错
}