zoukankan      html  css  js  c++  java
  • 赋值、递增和递减运算符

    赋值运算符

    赋值运算符左侧运算对象必须是可以修改的左值。
    赋值运算符满足右结合律。

    int ival,jval;
    ival = jval = 0; //正确,都被赋值为0
    

    复合赋值运算符

    任意一种复合运算符都等价于:

    a = a op b;
    

    唯一的区别是左侧运算对象的求值次数,使用复合运算符只求值一次,使用普通运算符则求值两次,这两次包含:

    • 一次时作为右边子表达式的一部分求值。
    • 另一次是作为赋值运算符的左侧对象求值。

    递增和递减运算符

    递增递减运算符有两个版本:

    • 前置版本,将运算对象加1或者减1,然后将改变后的对象作为求值的结果。
    • 后置版本,将运算对象加1或者减1,但是求值结果是运算对象改变之前的值。
    • 前置版本将对象本身作为左值返回。
    • 后置版本将对象原始值的副本作为右值返回。

    注意:
    除非必须,否则不要使用递增递减的后置版本。
    前置版本的递增运算符避免了不必要工作,它把值加1后直接返回改变了的运算对象,与之相比,后置版本则需要将原始值存储下来以便返回这个未修改的值,如果我们不需要修改前的值,那么后置版本操作就是一种浪费。
    对于整数和指针而言,编译器可能对这种额外的工作进行一定的优化,但是对于迭代器类型,这种额外的开销消耗巨大,建议使用前置版本。

    在一条语句中混用解引用和递增运算符

    如果想在一条复合表达式中即将变量的加1或减1又要使用它原来的值,此时就必须采用递增或递减的后置版本。
    例如,循环输出一个vector中的内容,直到遇到第一个负值为止:

    auto pbeg = v.begin();
    while(pbeg != v.end() && &pbeg >=0)
        cout<<*pbeg++<<endl;
    

    预算对象可按任意顺序求值

    大多数运算符没有堆顶运算对象的求值顺序,如果一条子表达式改变了某个运算对象的值,另一个子表达式又要使用这个值的话,运算对象的求值顺序就十分关键。因为递增和递减运算符会改变对象的值,所以要地方在复合表达式中错用这两个运算符。

    while(beg != s.end() &&!isspace(*beg))
        *beg = toupper(*beg++);     //错误,该赋值语句未定义
    

    赋值运算符左右两端的运算对象都用到了 beg,并且右侧的运算对象还改变了 beg 的值,所以该赋值语句是未定义的,编译器可以按照下面任意一种思路来处理该表达式:

    *beg = toupper(*beg);       //如果先求左侧的值
    *(beg+1) = toupper(*beg);   //如果先求右侧的值
    
  • 相关阅读:
    加法的位运算实现
    C++装饰器模式
    字符串类型的相互转换
    手算CRC及其实现
    Linux下搭建C/C++编程环境
    Deepin Linux 实体机安装
    Atom + Texlive 配置 Latex 环境
    有关字符串的算法(KMP,Manacher,BM)陆续补充
    Linux 下大文件分割与合并
    Ubuntu /目录满,发现是docker image 太多解决办法
  • 原文地址:https://www.cnblogs.com/xiaojianliu/p/12498255.html
Copyright © 2011-2022 走看看