C++11

1.新增不需要赋值即可初始化

    //C++98
    int a = 1;
    int* p1 = new int[3];
    Date d1(2022, 9, 26);

    //C++11
    Date d2{ 2022,9,27 };
    int* p2 = new int[3]{ 1,2,3 };
    int b{ 1 };
    Date* p4 = new Date[3]{ {2022,9,28},{2022,9,29},{2022,9,30} };

2.右值引用

1.左值引用 只能引用左值,不能引用右值

const 左值 可以引用左值,也可以引用右值

    //左值引用
    int c = 1;
    int& rc = c;
    //int& rv = 20;  ×  左值不允许引用右值
    const int& rv = 20;//因为20是常量  关乎到权限的问题 所以可以引用
    const int& rb = c;
2.右值引用
    //右值引用
    int&& r1 = 10;
    //int&& r2 = c; 右值引用不允许引用左值
    int&& rb = move(c);//move能把左值该为右值  但是他的数据会被转移 所以谨慎使用
    string s1("111");
    string s2 = (move(s1));
    //s1 的111被move转移到了s2  所以现在s1为空
两者的差别在与 坐值引用可以取地址  右值引用不可以取地址

3.可变模版参数

// Args是一个模板参数包,args是一个函数形参参数包
// 声明一个参数包Args...args,这个参数包中可以包含0到任意个模板参数。
template <class ...Args>
void ShowList(Args... args)
{}

4.lambda表达式

    //lambda表达式
    int d = 1;
    int e = 2;

    auto add1 = [](int a, int b)->int {return a + b; };
    add1(1, 2);

    auto add2=[](int a, int b){return a + b; };
    add2(1, 2);

    auto add3 = [=] {return d + e; };//全部传值
    //auto add3=[=]{return d=e;};
    //传值 不允许被修改
    add3();
    auto add4 = [&] {return d = e + 2; };//全部传引用
    add4();
    auto add5 = [&, d] {return e = d + 2; };//d用传值 其他全部传引用
    add5();
    auto add6 = [=, &d] {return d = e + 2; };//d用传引用 其他全部传值
    add6();

5.包装器

    //包装器
    function<int(int, int)> fun1 = f;
    fun1(1, 2);
    function<int(int, int)> fun2 = person::a;//调用静态成员函数
    fun2(1, 2);
    function<int(person,int, int)> fun3 = &person::b;//调用普通成员函数
    fun3(person(), 1, 2);

150. 逆波兰表达式求值 - 力扣(LeetCode)

class Solution {
public:
    int evalRPN(vector<string>& tokens) {
    stack<long long> s;
    map<string,function<long long(long long,long long)>> func=
    {
        {"+",[](long long a,long long b){return a+b;}},
        {"-",[](long long a,long long b){return a-b;}},
        {"*",[](long long a,long long b){return a*b;}},
        {"/",[](long long a,long long b){return a/b;}}
    };
    
    for(auto& e:tokens)
    {
        if(func.count(e))//判断e是否存在map中  存在就是操作符
        {
            long long right=s.top();
            s.pop();
            long long left=s.top();
            s.pop();

            s.push(func[e](left,right));
        }
        else//不存在就是操作数
        {
            s.push(stoll(e));
        }
    }
    return s.top();
    }
};

6.bind

    //bind
    function<int(int, int)> fun1 = bind(f,placeholders::_2,placeholders::_1);
    fun1(1, 2);//bind调整顺序
    function<int(int, int)> fun2 = person::a;//调用静态成员函数
    fun2(1, 2);
    function<int(person, int, int)> fun3 = &person::b;//调用普通成员函数  //不用bind时 function参数要加person
    fun3(person(), 1, 2);
    function<int(int, int)> fun4 = std::bind(&person::b,person(),placeholders::_1, placeholders::_2); //调用普通成员函数   用bind时 function参数不用加person
    fun4(1, 2);//bind调整参数个数

7.整体代码

#include<iostream>
#include<functional>
using namespace std;

class Date
{
public:
    Date(int y, int m, int d)
    {
        year = y;
        month = m;
        day = d;
    }

private:
    int year;
    int month;
    int day;
};

template<class T>
void a(T&& t)//传左值变左值 传右值变左值
{
    func(t);//这时候的t已经是左值了  
    //因为被模版折叠
    //但可以move改变为右值
    func(move(t));//但t的资源会被转移
    func(forward<T>(t));//完美转发 转为右值 并且t的资源不会被转移
}

class person
{
    //person() = default;
    //强制生存默认构造或者其他的拷贝赋值等...

    //person() = delete;
    //不让调用并且不让生存默认构造或者其他的拷贝赋值等...

public:

    static int a(int a, int b)
    {
        return a + b;
    }

    int b(int a, int b)
    {
        return a + b;
    }

};


// Args是一个模板参数包,args是一个函数形参参数包
// 声明一个参数包Args...args,这个参数包中可以包含0到任意个模板参数。
template <class ...Args>
void ShowList(Args... args)
{}

int f(int a,int b)
{
    return a + b;
}




int main()
{
    //C++98
    int a = 1;
    int* p1 = new int[3];
    Date d1(2022, 9, 26);

    //C++11
    Date d2{ 2022,9,27 };
    int* p2 = new int[3]{ 1,2,3 };
    int b{ 1 };
    Date* p4 = new Date[3]{ {2022,9,28},{2022,9,29},{2022,9,30} };

    //左值引用
    int c = 1;
    int& rc = c;
    //int& rv = 20;  ×  左值不允许引用右值
    const int& rv = 20;//因为20是常量  关乎到权限的问题 所以可以引用
    const int& rb = c;

    //右值引用
    int&& r1 = 10;
    //int&& r2 = c; 右值引用不允许引用左值
    int&& rb = move(c);//move能把左值该为右值  但是他的数据会被转移 所以谨慎使用

    string s1("111");
    string s2 = (move(s1));
    //s1 的111被move转移到了s2  所以现在s1为空



    //lambda表达式
    int d = 1;
    int e = 2;

    auto add1 = [](int a, int b)->int {return a + b; };
    add1(1, 2);

    auto add2=[](int a, int b){return a + b; };
    add2(1, 2);

    auto add3 = [=] {return d + e; };//全部传值
    //auto add3=[=]{return d=e;};
    //传值 不允许被修改
    add3();
    auto add4 = [&] {return d = e + 2; };//全部传引用
    add4();
    auto add5 = [&, d] {return e = d + 2; };//d用传值 其他全部传引用
    add5();
    auto add6 = [=, &d] {return d = e + 2; };//d用传引用 其他全部传值
    add6();

    //包装器
    function<int(int, int)> fun1 = f;
    fun1(1, 2);
    function<int(int, int)> fun2 = person::a;//调用静态成员函数
    fun2(1, 2);
    function<int(person,int, int)> fun3 = &person::b;//调用普通成员函数
    fun3(person(), 1, 2);

    //bind
    function<int(int, int)> fun1 = bind(f,placeholders::_2,placeholders::_1);
    fun1(1, 2);//bind调整顺序
    function<int(int, int)> fun2 = person::a;//调用静态成员函数
    fun2(1, 2);
    function<int(person, int, int)> fun3 = &person::b;//调用普通成员函数  //不用bind时 function参数要加person
    fun3(person(), 1, 2);
    function<int(int, int)> fun4 = std::bind(&person::b,person(),placeholders::_1, placeholders::_2); //调用普通成员函数   用bind时 function参数不用加person
    fun4(1, 2);//bind调整参数个数

    return 0;
}
posted @ 2022-09-26 21:50  lemon-Breeze  阅读(34)  评论(0编辑  收藏  举报