一、先看下面两段完全一样的代码块

/* test.cpp */
int main()
{
int a = 5;
++a = 7;
printf("%d\n", a);
return 0;
}
/* test.c */
int main()
{
int a = 5;
++a = 7;
printf("%d\n", a);
return 0;
}

  在test.cpp文件与test.c文件下会分别显示什么呢?运行结果显示,在test.cpp下打印出 7 , 而在test.c下编译出错,报错信息:

二、前置自增

  乍一看++a = 7; 这条语句很奇怪,本以为会在C++里编译报错,没想到居然成功输出了7。

  学过C一定对前置自增“先+1,再返回”的操作很熟悉了,++a 会对a值先+1,再返回a当前的值(也就是6),注意在C里返回的是“值”(value)而不是 “引用”(reference),因此在test.c中 ++a = 7; 由于++a返回的是6这个右值,因此也就不能作为=的左操作数。

  而在C++里由于加入了引用这个概念,因此,++a会先对a值+1,再返回a的引用(是一个左值)。因此在C++标准中对于前置自增的运算符重载操作返回的也是 Object& 而不是 Object。

三、后置自增

  相对于前置自增,后置自增的操作是“先返回当前值,再+1”,也即 a++ 执行的是 int tmp = a; ++a; return tmp; 后置自增无论在C里还是C++里返回的都是值(Value),因此在后置自增上并没有太大的区别。由于后置自增返回的是值(Value),因此对于a++ = 7;这条语句,不论是在C++还是C中都会编译报错的。

  说到这可能有人会想到,既然C++里加入的引用可以作为前置自增的返回类型,为什么后置自增的返回不用引用呢?

  (1)首先,a++ <==> { int tmp = a; ++a; return tmp;  } ,tmp是一个临时变量,无法返回其引用。

  (2)在C++ Primer中明确说明了,C++中前置自增返回的是引用,后置自增则将对象原始值的副本作为右值返回既然要作为右值返回,后置自增的运算符重载的返回类型 就应该是 const Object,这样对于任何一个以 const Object作为返回类型的后置自增运算符重载,类似于 a++ = 7这样的语句都会报错,也即 a++返回了一个右值(rvalue)

四、运算符重载示例

  关于前置++后置++的重载,详细可查<<More Efficitive C++ >> 条款6;

class A {
public:
A(int a) : m_data(a) {} A& operator++(){ //前置自增,返回 Object &
m_data += 1;
return *this;
} const A operator++(int) { //后置自增, 返回 const Object ,右值
A tmp(m_data);
++*this;
return tmp;
} A& operator=(const A& a) {
this->m_data = a.m_data;
return *this;
}
//private:
int m_data;
}; /* test.cpp */
int main()
{
A a(5);
A b(10);
++a = b; // ++a返回a本身,>> a.m_data = 10;
cout << a.m_data << endl;
cout << (b++).m_data << endl; // b++返回tmp副本作为右值,>> 10
//(b++) = a; //error, b++返回的是右值 }

五、参考

  <<More Efficitive C++ >> 条款6;

  <<C++ Primer 5th 中文版>> 4.5 递增和递减运算符

  

C和C++区别——前置自增与后置自增的更多相关文章

  1. C++之前置自增与后置自增

    关于前置自增与后置自增的区别我是参考这里:http://bbs.bccn.net/thread-454977-1-1.html 简单复述下,比如++x; 与 x++; 在C中,++x这个表达式的值为原 ...

  2. c++重在运算符前置自增和后置自增

    class student { int age; }; int main() { class student stu; (stu++)++;//error ++(stu++);//error stu+ ...

  3. C: printf参数执行顺序与前置后置自增自减的影响

    起源: 今天在了解副作用side-effect的过程中,看到了下面的网页,把我带到了由printf引起的一系列问题,纠结了一整天,勉强弄懂. 第一个代码没什么好解释的.而第二个printf(" ...

  4. HTML5 选择前置摄像头,选择后置摄像头

    最近发现我写的都是乱七八糟的,觉得应该给大家带点福利,于是写了这篇 背景:最近想做个web应用,需要用到摄像头,但是发现默认一直是前置摄像头,拍照很麻烦,于是找了很多文章,居然没有人提到,只好FQ去找 ...

  5. c++ 前置++与后置++的区别

    用C++编程的都知道,C++提供了一个非常强大的操作符重载机制,利用操作符重载,我们可以为我们自定义的类增加更多非常有用的功能.不过,C++也有限制,就是当我们为自定义的类重载操作符时,重载操作符的含 ...

  6. C++之运算符重载(前置++和后置++)

    今天在阅读<google c++ 编程风格>的文档的时候,5.10. 前置自增和自减:有一句话引起了我的注意: 对于迭代器和其他模板对象使用前缀形式 (++i) 的自增, 自减运算符.,理 ...

  7. C++中前置操作符和后置操作符的重载

    1,C 语言中讨论了原生含义,C++ 中有必要考虑前置.后置操作符能够重载,有何问题: 2,值得思考的问题: 1,下面的代码有没有区别?为什么? 1,i++  // i 的值作为返回值,i 自增 1: ...

  8. android Camera 如何判断当前使用的摄像头是前置还是后置

    现在 android 平台的智能手机一般都标配有两颗摄像头.在 Camera 中都存在摄像头切换的功能. 并且有一些功能前后置摄像头上会有所不同.譬如人脸检测,人脸识别,自动对焦,闪光灯等功能, 如果 ...

  9. pytest_前置后置

    今天总结下pytest,pytest简直就是python自动化中的高富帅,各种操作,哈哈 这次总结主要涉及到了以下几点: 1.unittest中的setUp.tearDown.setUpClass.t ...

随机推荐

  1. Python3 字典浅析

    Python 字典 字典(Dictionary) 字典是一个无序.可变和有索引的集合.在 Python 中,字典用花括号编写,拥有键和值. 实例 创建并打印字典: thisdict = { " ...

  2. springboot2.x基础教程:自动装配原理与条件注解

    spring Boot采用约定优于配置的方式,大量的减少了配置文件的使用.该框架使用了特定的方式来进行配置,从而使开发人员不再需要定义样板化的配置. 当springboot启动的时候,默认在容器中注入 ...

  3. 【NOIP2013模拟】黑魔法师之门

    题目描述 经过了16个工作日的紧张忙碌,未来的人类终于收集到了足够的能源.然而在与Violet星球的战争中,由于Z副官的愚蠢,地球的领袖applepi被邪恶的黑魔法师Vani囚禁在了Violet星球. ...

  4. 提高SSH服务安全,ssh黑白名单

    1.调整sshd服务配置,并重载服务 # vim /etc/ssh/sshd_config PermitRootLogin no                     #禁止root用户登录 Use ...

  5. Idea没安装几款好用的插件,怎么风骚的写代码???

    ​ 工欲善其事,必先利其器,好的工具可以提升我们的开发效率,越来越多的Java程序员从Eclipse转到了Jetbrains家的Idea.今天给大家介绍的是我常用的十几款Idea必装的插件. ​ Ti ...

  6. oracle之二表和表空间的关系

    表和表空间的关系 建一个使用缺省值的表空间SQL> create tablespace a datafile '/u01/data/urpdb/a01.dbf' size 10m; 利用orac ...

  7. UI中列表

    1.ul.ol.dl

  8. sql注入 报错注入常用的三种函数

    1.floor()函数 报错原因是 报错的原因是因为rand()函数在查询的时候会执行一次,插入的时候还会执行一次.这就是整个语句报错的关键 前面说过floor(rand(0)*2) 前六位是0110 ...

  9. [剑指Offer]65-不用加减乘除做加法

    题目 写一个函数,求两个整数之和,要求在函数体内不得使用+.-.*./四则运算符号. 题解 用位运算模拟加法的三步: 无进位加法:异或运算. 进位:与运算再左移一位. 直到进位为0结束. 代码 pub ...

  10. vue | 基于vue的城市选择器和搜索城市对应的小区

    城市选择器应该是比较常用的一个组件,用户可以去选择自己的城市,选择城市后返回,又根据自己选择的城市搜索小区. 功能展示 这是选择结果 这是选择城市 这是搜索小区 这是搜索小区接口,key为城市名字,i ...