Skip to content

万能引用 ​

c++
int main()
{
	test1(9.11); //9.11
	test2(9.13); //9.13
	test3(9.18); //9.18
	test4(92.18); //92.18
	test5(98.18); // d 98.18
	MyVector1<int>::push_back(9.8); //9
	MyVector1<int>::push_back2(9.8); //9.8
	MyVector2::push_back(9.8);//9.8
	test6();
	test7(80.88);//80.88

	//传入一个右值 此时fun1 的T&&就是一个右值引用 
	//但是y本身是左值 所以又传了一个左值给fun2
	fun1(55);//55 
	
	fun10(99);//99
	return 0;
}
c++
// #include "vld.h"
/*
	万能引用是既可以被编译期处理为左值引用,
	又可以被编译期处理为右值引用。不是既是
	左值引用又是右值引用,不违背C++一个引用
	不是左值引用,就是右值引用的基本说法,
	万能引用会在编译期被当做左值引用或右值
	引用处理。
*/
//*************************************
// 万能引用 引用类型根据编译期传入的值来确定
template <typename T>
void test1(T &&y)
{
	std::cout << y << "\n";
}
//*************************************
//  常量左值引用
/*
	这是因为在这个函数中,参数 "y" 被声明为
	一个常量左值引用。这意味着它可以接受任
	何类型的参数,包括右值。当一个右值传
	递给一个常量左值引用时,编译器会自
	动创建一个临时变量来存储该值,并
	将该变量的引用传递给函数。因此
	,即使参数是一个左值引用,它
	仍然可以接受右值。
*/
template <typename T>
void test2(const T &y)
{
	std::cout << y << "\n";
}

//*********************************
// 右值引用  接收右值
template <typename T>
void test3(const T &&y)
{
	std::cout << y << "\n";
}
//*********************************
// 值传递
template <typename T>
void test4(const T y)
{
	std::cout << y << "\n";
}
//*********************************
// 值传递
template <typename T>
void test5(T y)
{
	std::cout << typeid(y).name() << " " << y << "\n";
}
//********************************
// 不是万能引用
template <typename T>
class MyVector1
{
public:
	static void push_back(T &&elem)
	{
		std::cout << elem << "\n";
	}
	// 是万能引用
	template <typename A>
	static void push_back2(A &&elem)
	{
		std::cout << elem << "\n";
	}
};
//**********************************
// 是万能引用
class MyVector2
{
public:
	template <typename T>
	static void push_back(T &&elem)
	{
		std::cout << elem << "\n";
	}
};
//**********************************
/*
	auto&& 就是万能引用。
	const auto&& var 就不是万能引用了。
*/
void test6(){
	int i = 0;
	//传左值 就是左值引用
	auto&& elem = i;
	//传右值就是右值引用
	auto&& elem2 = std::move(i); 
}

//**************************************************************
//引用折叠
template<typename T>
/*当被认为是左值引用的时候 
类型应该是 T& &&  此时
类型被折叠为T&
*/
void test7(T&& y){
	std::cout<<y<<"\n";
}

//***********************************************************
/*   int&& rrefI = 10; rrefI
	 是一个右值引用但是rrefI
	 本身是个左值

     3.万能引用的作用,就是当参数为
	 左值时。T&&为左值。当参数为右
	 值时,T&& 为右值。就这么简单。
*/
template<typename T>
void fun2(T&& y){
	std::cout<<y<<"\n";
}

template<typename T>
void fun1(T&& y){//万能引用了 
	fun2(y);
}
//**************************************************************
// 完美转发
template<typename T>
void fun20(T&& y){
	std::cout<<y<<"\n";
}

template<typename T>
void fun10(T&& y){
	//forward可以推断出它之前是什么值?
	fun20(std::forward<T>(y));
}

学 习 记 录