zoukankan      html  css  js  c++  java
  • C/C++拾遗

    枚举是一个常量整型的列表,如enum boolean {NO, YES};则,第一个值为0,第二个值为1


    类型转换:

    自动转换:将“比较窄的”操作数转换为“比较宽的”操作数,且不丢失信息。

    当把较长的整数转换为较短的整数或char型时,超出的高位部分将被丢弃。

    强制类型转换只是生成一个指定类型的n值,n本身并没有改变,如sqrt((double)n);

    浮点数在内存中的表示:http://www.cnblogs.com/xkfz007/archive/2012/02/27/2370357.html

    浮点数二进制与十进制的转换:http://www.cnblogs.com/xkfz007/articles/2590472.html(X86使用的是反字节序,printf对于类型不匹配的处理)


     printf函数:

      x,d等等这些都是以int形式输出,若是要以浮点数形式输出,则需要%f,%e,%g等等

      printf函数参数的入栈是从右往左,比如下面这个程序:

    int main(int argc, char *argv[])
    {
        char* a[] = {"hello","the","world"};
        char **p = a;
        printf("%p %p\n",*p,*(++p));
        return 0;  
    }

    结果为:004012B5  004012B5,在运算p之前已经进行了++p操作


    求两数的平均数:

    int f(int x,int y)
    {
        return (x&y)+((x^y)>>1);
    }

    判断一个数是不是2的N次方:

    !(x&(x-1));  //若是则为真,否则为假

     找出两个数中比较大的:

    //方案一
    int max = ((a+b)+abs(a-b))/2;
    
    //方案二
    int c = a-b;
    c = unsigned(c) >> (sizeof(int)*8 -1);

    将两个数交换:

    //当a,b比较大的时候,会出现超界的问题
    a = a+b;
    b = a-b;
    a = a-b;
    //这个不会出现超界的问题
    a = a^b;
    b = a^b;
    a = a^b;

    内存对齐:

    sizeof与strlen的:

    形如 (void*)0的指针问题:

    #define FIND(struc,e) (size_t)&(((struc*)0)->e)
    //这段代码的意思是找出e在结构体struc中的偏移位置
    //其中(struc*)0是将0强制转化为指向struc的指针

     typedef两个作用

    1. 使程序参数化,提高程序的可移植性。如果typedef声明的数据类型同机器有关,那么当移植到其他机器上时,只需改变typedef类型定义即可。
    2. 为程序提供更好的说明性,使新的类型名字面意义更直观。

     引用的用法:

      引用其实是一个变量的一个别名,并不产生副本。在底层实现上,引用其实保存的也是变量的实际地址,只不过系统将这些细节透明化了,让我们宏观上觉得引用是变量的一个别名。

    • 传递可变参数。如swap(int &a,int &b);
    • 传递大型对象。防止复制对象副本,提高效率
    • 引用返回值。比如一个函数返回了一个引用类型的值
      int& max(int& a,int& b)
      {
          return a>b?a:b;
      }    
      int main(int argc, char *argv[])
      {
          int b = 10;
          int c = 11;
          max(b,c) = max(b,c)+5;
      //c的值为16 }

      引用作为返回值必须遵守以下规则:①不能返回局部变量的引用。主要原因是局部变量会在函数返回后被销毁,因此被返回的引用就成为了'无所指'的引用,程序会入未知状态。②不能返回函数内部new分配的内存的引用。虽然不存在局部变量的被动销毁问题,可对于这种情况(返回函数内部new分配内存的引用),又面临其它尴尬局面。例如,被函数返回的引用只是作为一个临时变量出现,而没有被赋予一个实际的变量,那么这个引用所指向的空间(由new分配)就无法释放,造成memory leak。③可以返回类成员的引用,但最好是const。主要原因是当对象的属性是与某种业务规则(business rule)相关联的时候,其赋值常常与某些其它属性或者对象的状态有关,因此有必要将赋值操作封装在一个业务规则当中。如果其它对象可以获得该属性的非常量引用(或指针),那么对该属性的单纯赋值就会破坏业务规则的完整性。

    • 常引用。const int &ra = a;常引用的意思是,不能通过该引用ra来修改a的值。
      //有下面函数声明
      string foo();
      void bar(string &s);
      //下面的调用是非法的
      bar(foo());
      bar("Hello!");
      //将bar函数改成如下就可以通过
      void bar(const string &s);

      这里是因为foo()和"Hello"会产生一个临时对象,这些临时对象都是const类型的,将一个const的类型转化为非const类型,是不允许的。

    • 引用总结:①在引用的使用中,单纯给某个变量取个别名是毫无意义的,引用的目的主要用于在函数参数传递中,解决大块数据或对象的传递效率和空间不如的问题。②用引用传递函数的参数,能保证参数传递中不产生副本,提高传递的效率,且通过const的使用,保证了引用传递的安全性。③引用与指针的区别是,指针通过某个指针变量指向一个对象后,对它所指向的变量间接操作。程序中使用指针,程序的可读性差;而引用本身就是目标变量的别名,对引用的操作就是对目标变量的操作。④使用引用的时机。流操作符<<和>>、赋值操作符=的返回值、拷贝构造函数的参数、赋值操作符=的参数、其它情况都推荐使用引用。

    拷贝构造函数:

    • 特殊的构造函数,函数名与类名相同,没有返回值
    • 只有一个参数,为同类对象的引用
    • 每个类都有一个拷贝构造函数,以实现同类对象之间的数据成员传递。如果程序员没有定义,则系统提供一个默认的。
    • 默认构造函数是将对象1各个域的值都拷贝给了对象2相应的域。当用赋值操作符“=”时,会调用拷贝构造函数。
    View Code
    class point
    {
        public:
            point(int a,int b)
            {
                x = a;
                y = b;
            }    
            point(const point &p)
            {
                x = p.x;
                y = p.y;
            }    
            void print()
            {
                cout<<x<<" "<<y<<endl;
            }    
        private:
            int x,y;
    };    
    
    int main(int argc, char *argv[])
    {
        point p1(30,40);
        point p2(p1);
        p1.print();
        p2.print();
      system("PAUSE");    
      return 0;
    }
  • 相关阅读:
    关键词学英语----设计模式
    nginx配置
    文件File类型接收
    md工具
    springboot集成Spring Data JPA
    maven应用
    2019年Java面试题基础系列228道(3)
    2019年Java面试题基础系列228道(2)
    2019年Java面试题基础系列228道(1)
    天空盒
  • 原文地址:https://www.cnblogs.com/7ants/p/3015065.html
Copyright © 2011-2022 走看看