c++引用传参真的这么神奇吗?

上案例(重点关注函数传值方式)

案例1:

#include<bits/stdc++.h>
using namespace std;
//int ***ans;
int process1(int i, int j, int step, const vector<vector<vector<int>>> ans);
int main(){
    int x, y, step;
    cin>>x>>y>>step;
    step++;
    vector<vector<vector<int>>> ans(step, vector<vector<int>>(10, vector<int>(9)));
    ans[0][x][y] = 1;
    for(int k = 1; k < step; k++){
        for(int i = 0; i < 10; i++){
            for(int j = 0; j < 9; j++){
                  ans[k][i][j] = process1(i - 1, j + 2, k - 1, ans)
                        +process1(i - 2, j + 1, k - 1, ans)
                        +process1(i + 2, j + 1, k - 1, ans)
                        +process1(i + 1, j + 2, k - 1, ans)
                    +process1(i + 1, j - 2, k - 1, ans)
                    +process1(i + 2, j - 1, k - 1, ans)
                    +process1(i - 1, j - 2,k - 1, ans)
                    +process1(i - 2, j - 1, k - 1, ans);
            }
        }
    }
    cout<<ans[step-1][0][0]<<endl;
    
    return 0;
}


int process1(int i, int j, int step,const vector<vector<vector<int>>> an){
    if(i > 9 || i < 0 || j < 0 || j > 8){
        return 0;
    }
    return an[step][i][j];
        
}


结果1

_-- 整整花了我1001ms, 这什么概念? 1秒, 一台普通计算机能够执行几百万条指令的时间 (尴尬)
在这里插入图片描述

神奇的地方来了,请看 ^ - ^
案例2:

#include<bits/stdc++.h>
using namespace std;
//int ***ans;
int process1(int i, int j, int step, const vector<vector<vector<int>>> &ans);
int main(){
    int x, y, step;
    cin>>x>>y>>step;
    step++;
    vector<vector<vector<int>>> ans(step, vector<vector<int>>(10, vector<int>(9)));
    ans[0][x][y] = 1;
    for(int k = 1; k < step; k++){
        for(int i = 0; i < 10; i++){
            for(int j = 0; j < 9; j++){
                  ans[k][i][j] = process1(i - 1, j + 2, k - 1, ans)
                        +process1(i - 2, j + 1, k - 1, ans)
                        +process1(i + 2, j + 1, k - 1, ans)
                        +process1(i + 1, j + 2, k - 1, ans)
                    +process1(i + 1, j - 2, k - 1, ans)
                    +process1(i + 2, j - 1, k - 1, ans)
                    +process1(i - 1, j - 2,k - 1, ans)
                    +process1(i - 2, j - 1, k - 1, ans);
            }
        }
    }
    cout<<ans[step-1][0][0]<<endl;
    
    return 0;
}


int process1(int i, int j, int step,const vector<vector<vector<int>>> &an){
    if(i > 9 || i < 0 || j < 0 || j > 8){
        return 0;
    }
    return an[step][i][j];
        
}


啊!!!!!
改了什么?答案打在公平上。
就在参数名前加了两个 ‘&’ 符号,也就是说,传参方式从按值传值变成了按引用传值

结果2

花了俺5ms

在这里插入图片描述

干货

1.STL里面的容器也是按值传参的(这也就导致了如果将过大的STL容器作为参数的话)
首先, 申请一块和实参ans一样大小的空间(案例中的ans占用空间老大了!), 再把实参ans复制(拷贝)到这个空间中。没错,这个空间就是形参an的内存空间。由于整个复制过程过于耗费资源(或者说既费时,又费空间),导致真个算法被拖垮
怎么解决呢
2.采用按引用传参的方式,既省时又省空间
从形式上来说,按引用传参就是在函数声明和函数定义时,在参数名正前方加上&的符号, 每个&对应着一个参数。凡是加上了&的参数,函数都会按引用传递它。
从此,函数走向巅峰…开个玩笑
首先,编译器再不会像没加&一样,为an形参申请一块和实参ans一样大小的空间(案例中的ans占用空间老大了!), 再把实参ans复制(拷贝)到这个空间中。没错,既不要复制的动作,也不要格外的空间了。那你就奇怪了,那使用哪里的空间呢?使用main函数中ans的空间。也就是说,使用实参的空间。
3.那么什么是引用呢?
I.声明和初始化定义在一个表达式中:
像 int *a;
不不不,俺又搞事情了,虽然指针和引用有点像
应该是 int &a = x;
有同学问了,x是啥?问题就是这里,我故意的。哈哈,为了让你记住x可以是一个变量名,解除引用的指针变量(比如
int *x = new int;
x = 2;
int &a = b; ), 数组元素,结构成员,引用。这种x也叫做可被引用的数据对象-----左值。而x不可以为-含有多项的表达式,字面常量(也就是我们看到的 1 , ’a’, ”dfddf“,a+b
c)
标准的像这样:

int a = 9int &x = a;

double a = 9.0double &x = a;

char c = 'a'char &x = c;

int a[8] = {0};
int& x = a[4];

友情提示:不要熬夜哦。俺先睡了,稍后更新。喜欢的小伙伴记得关注哦

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值