- 常量
- 宏常量 #define 常量名 常量值
- 使用const修饰
- 数据类型
- long long 长长整型,long long b = 3;
- 字符型存储的不是字符,而是对应的ASCII编码;
- 字符串
- char 变量名[] = "字符串"
char str[] = "hello";
- string 变量名 = “字符串”
string s = "world";
- bool类型
占一个字节,true其实就是1, false其实就是0; - 数据输入
cin >> 变量名,对应cout,注意箭头的方向。
int i = 1;
cout << "please input int value: " << endl;
cin >> i;
cout << "i = " << i << endl;
- 三目运算符
c = a > b ? a : b;
三目运算符返回的是变量可以继续赋值;
int m = 1, n = 2, k = 3;
m > n ? m : n = 4;
cout << "m = " << m << " n = " << n << endl;
输出:m = 1 n = 4
- 函数
返回值 函数名(参数列表){ },和Java还是有些区别,没有访问控制符呢。
#include <iostream>
#include <string>
using namespace std;
void printName(string s);
int main() {
printName("C++");
return 0;
}
void printName(string s) {
cout << "Name is: " << s << endl;
}
上边的例子中我们提前对函数进行了声明(函数声明),函数声明没有函数体。
- 指针
指针变量的定义:数据类型 * 指针变量名;
#include<iostream>
using namespace std;
int main() {
int a = 10;
int * p;
p = &a;
*p = 20;
cout << "a= " << a << endl;
return 0;
}
&a是取a的地址,*p是解地址运算符。
- 常量指针
const int * p = &a;
常量指针的指向可以修改,但是指针指向的值不可修改。
int * const p = &a;
指针常量的指针的指向不可以修改,但指针指向的值可以修改。
const int * const p = &a;
const既修饰指针又修饰常量,指针的指向和指针指向的值都不可修改。 - 结构体
struct 结构体名称 {成员列表}
struct Student
{
string name;
int age;
float score;
};
struct Student s1;
s1.name = "lkk";
s1.age = 20;
s1.score = 56.5f;
结构体指针:struct Student * p = &s1;
通过-> 访问结构体变量 p->name = "oi";
- new操作符
int * p = new int(10);
new操作符创建一个整数数据,返回值为该数据类型的指针。
如果想释放堆区的数据,使用delete,delete p
释放数组要加[]号,delete [] arr - 引用
- 引用就是给变量起别名,语法:数据类型 &引用名称 = 原名;
- int a = 10; int &b = a;
- 引用必须要初始化,比如 int &b; // 错误的
- 引用一旦初始化就不能更改;
感觉这个引用和Java中的引用不太一样呢。 - 引用做函数参数时,和指针到达的效果一样,同样可以修改原数据的值。
- 如果函数的返回值是一个引用,那这个函数可以作为左值进行使用,比如
int& test()
test() = 20;
- 引用的本质是一个指针常量。
- 常量引用一般用来修饰形参,防止误操作。
- 默认参数
- 函数的某个参数带默认值,那之后的参数必须都带默认值
- 函数的声明和实现只能有一个带默认值
- 占位参数
返回值 函数名(数据类型){}
占位参数只有数据类型,没有参数名称。
占位参数可以有默认参数。 - 访问权限
- public 公共权限,类外可访问
- protected 子类可访问,其他类不可访问
- private 私有权限,类外不可访问
struct 和class唯一的区别是默认访问权限不同,struct默认权限是公共权限,class默认权限是私有权限。
- 构造函数和析构函数
构造函数和析构函数负责对象的初始化和清理工作,由系统自动调用,空实现。
构造函数:类名() {}
析构函数:~类名() {},析构函数不可以有参数,不可发生重载,对象销毁前系统自动调用。
Person p1;
Person p2(5);
Person p3 = Person(5);
Person p4 = 5;
构造函数的调用方式如上。
创建一个类之后,编译器会创建默认构造函数,析构函数和拷贝构造函数。如果提供了有参构造函数,则编译器不在生成默认构造函数。
- 初始化列表
Person(int a): _age(a) {
}
- 静态成员
- 静态成员在类内声明,在类外初始化
class Person
{
public:
static int id;
Person()
{
cout << "构造函数" << endl;
}
Person(int age) {
_age = age;
}
Person(int a): _age(a) {
}
~Person()
{
cout << "析构函数" << endl;
}
private:
int _age;
};
int Person::id = 2;
- 静态成员的访问方式有两种,通过对象访问和通过类名访问
Person p(20);
p.id;
或者
Person::id
- 静态成员函数只能访问静态成员变量。
- 静态成员函数也有两种访问方式,Person::func(),p.func()
- this对象指针
- this是指向当前对象的指针;
- *this是对象本省
- 友元
友元的关键字为friend,通过友元可以在类外访问类的私有变量。
全局函数和类做友元,需要在类的内部进行声明即可。
class A {
// 全局函数做友元
friend void fun();
// 类做友元
friend class B;
// 成员函数做友元
friend void B::test();
}
void fun() {
}
class B {
public:
void test() {}
}
-
继承
语法:class 子类:继承方式 父类。
继承方式分为:公共继承,保护继承和私有继承。
先执行父类的构造函数在执行子类的构造函数,析构函数和构造函数的执行顺序相反。
如果想访问父类中同名的成员变量,需要加父类的作用域,比如:sun.father::value,成员函数同理,sun.father::fun()
C++ 允许多重继承,一个子类继承多个父类,语法:class sun: public father1, public father2 菱形继承
菱形继承会导致数据重复的问题,比如B,C继承A,D继承B,C。
公共继承前加virtual,变为虚继承,虚继承可以解决数据重复的问题。
class D:virtual public B,virtual public C {}多态
动态多态需要有继承关系,子类重写父类的虚函数。纯虚函数和抽象类
纯虚函数的语法:virtual void fun() = 0;
如果一个类中有纯虚函数,那这个类就是抽象类,抽象类不能实例化,子类必须重写抽象类的纯虚函数,否则也属于抽象类。虚析构和纯虚析构
虚析构的语法:virtual ~类名() {}
纯虚析构的语法:virtual ~类名() = 0
如果是纯虚析构,则该类属于抽象类,无法实例化对象。文件
文件类型分为两类:文本文件和二进制文件
ofstream 写文件,ifstream 读文件,fstream 读写文件
参考: