美文网首页
C/C++基础(5)

C/C++基础(5)

作者: 想起个帅气的头像 | 来源:发表于2020-10-02 23:58 被阅读0次

C++

namespace


#include <stdio.h>
#include <iostream>

using namespace  std;

int g_a = 10;

namespace spaceA {
    int g_b = 10;
}

namespace spaceB {
    namespace spaceC {
        struct Student {
            int id;
            char name[40];
        };
    }

    namespace spaceD {
        struct Student {
            int id;
            char name[40];
        };
    }
};

int main(void) {
    
    //using spaceA::g_b;
    cout << g_a << endl;
    cout << spaceA::g_b << endl;
    
    using spaceB::spaceC::Student;
    
    Student s;

    return 0;
}

引用

引用的本质是变量的别名
int a = 10;
int &b = a;
"数据类型 &" 表示引用
说明:

  1. 引用没有定义,是一种关系型的声明。声明它和原有变量的关系,因此类型也与原类型保持一致,且不分配内容。与原变量有相同的地址。
  2. 声明的时候必须初始化,且一经声明,不可变更。
  3. 可对引用,再次引用。多次引用的结果,使某一变量具有多个别名。
  4. & 符号前有数据类型是引用,其他皆为取地址。

引用本质理解

引用所占用的大小跟指针相等。本质是一个常指针,即 int * const a;

//两者本质是一样的
void modify(int *const a) {
    *a = 300;
}
//引用作为函数参数时,编译器会取地址给引用
void modify (int &a ) {
    //对一个应用进行赋值操作时,编译器会隐藏取*的操作
    a = 300;
}
常见用法
  1. 引用作为返回值,不建议返回局部变量的引用。如下:
int& getValue() {
    int a = 10;
    return a;
}
int main(void) {
    int main_a = 0;
    main_a = getValue(); 
    cout << "mian_a" << main_a << endl;  //此时成功,因为是值拷贝,对10进行赋值
    int &main_a_re = getValue(); //
    cout << "mian_a_re" << main_a_re << endl; //此时失败,因为引用地址的值拷贝,getValue中的a变量在此时已经被回收,无法被引用到。
    return 0;
}

这样导致外部方法在接受a的引用,当此方法被执行结束回收后,外部的a的应用将失效。

  1. 引用作为返回值,如果是静态变量或者堆中的变量,则可以作为左值对内部进行修改。
int& getValue() {
    static int a  = 10;
    return a;
}
int main(void) {
    getValue() = 1000;
}

指针引用

使用指针引用,极大的简化了对二级指针的操作,相当于直接操作变量本身。

struct teacher {
  int id;
  char name[64];
}
int get_mem(struct teacher * &tp) {
  tp = (struct teacher *)malloc(sizeof(struct teacher));
  tp->id = 100;
  strcpy(tp->name, "cb");
  return 0;
}
int free_mem(struct teacher * &tp) {
  if(tp != NULL) {
    free(tp);  
    tp = NULL;
  }
}
int main(void) {
  struct teacher * tp = NULL;
  get_mem(tp);
  get_free(tp);
}

使用二级指针的写法,需要在内部定义临时变量。

struct teacher {
  int id;
  char name[64];
}
int get_mem(struct teacher ** tpp) {
 struct teacher *tp = NULL;
  tp = (struct teacher *)malloc(sizeof(struct teacher));
  if(tp ==NULL) {
    return -1;
  }
  tp->id = 100;
  strcpy(tp->name, "cb");
  *tpp = tp;
  return 0;
}
int free_mem(struct teacher ** tpp) {
 struct teacher *tp = *tpp;
  if(tp != NULL) {
    free(tp);  
    *tpp = NULL;
  }
}
int main(void) {
  struct teacher * tp = NULL;
  get_mem(&tp);
  get_free(&tp);
}

内联函数

inline int max(int a,int b) {
  return a>b?a:b;
}
  1. 内联函数主要为了解决简单方法频繁的压栈出栈的处理,编译器根据实际的开销灵活处理。
  2. 编译器直接将函数体插入到调用位置,在编译期间处理,而宏定义在预处理阶段处理。
  3. 不能存在任何形式的循环条件,不能存在过多的条件判断,函数体不能过大,内联函数的声明必须在调用语句前

默认参数

int sum(int a = 0; int b = 0) {
  return a+b;
}

int main(void) {
  sum();
  sum(1);  //1作为参数a
  sub(1,2); 
}

默认参数需要从右往做开始默认,不允许前一个有默认参数,而后一个没有

占位参数

int sum(int a, int)  {
  return a;
}

int max(int a = 0, int = 0) {  //亚元
  return a;
}

占位参数主要用于函数重载,没有实际意义。

相关文章

网友评论

      本文标题:C/C++基础(5)

      本文链接:https://www.haomeiwen.com/subject/lzeiuktx.html