const用法
#include <iostream>
using namespace std;
int main()
{
const int a=100;
int b=200;
int c=300;
const int *p=&a;
cout<<*p<<endl;
int * const p2=&b;
cout<<*p2<<endl;
*p2=500;
cout<<*p2<<endl;
return 0;
}
define用法与弊端
#include <stdio.h>
#define MAX( a, b ) ((a>b)?(a):(b))
int main()
{
int x, y, max;
scanf("%d%d",&x,&y);
max = MAX( ++x, y );
max=MAX(x,++y);
printf( "max=%d\n", max );
return 0;
}
作用域标识符::
#include <iostream>
using namespace std;
int a=100;
int main()
{
int a=200;
cout<<a<<endl;
cout<<::a<<endl; //c++增加作用域标识符:: 用于对与局部变量同名的全局变量进行访问。
return 0;
}
// new 和delete 运算符(c语言中 malloc,free)
//new运算符可以创建堆空间
//语法:
//指针变量=new 数据类型;
//指针变量=new 数据类型[长度n];
//int *p; p=new int;
//char *pstr=new char[50];
new一个新对象包括:
*内存分配(operator new)
*调用构造函数
delete释放一个对象
*调用析构函数
*释放内存(operator delete)
#include <iostream>
using namespace std;
int main()
{
int *p=new int;
cout<<*p<<endl; // 数据随机的
p=new int(10); //分配内存时赋初值
cout<<*p<<endl;
int *p2=new int[10];
delete p;
delete [] p2;
return 0;
}
结构体内存对齐
#include <iostream>
using namespace std;
struct Test
{
int a;
double b;
char c;
double d;
};
int main()
{
Test test;
int *p=&test.a;
cout<<p<<endl;
p=(int *)&test;
cout<<p<<endl;
cout<<sizeof(test.a)<<endl;
cout<<sizeof(Test)<<endl;
//内存地址相同,所以结构体第一个成员与结构体变量的偏移量为0
//其他成员要对齐到某个数字(对齐数)的整数倍的地址
//对齐数取编译器预设的一个对齐整数与该成员的大小的较小值
//结构体总大小为最大对齐数的整数倍
return 0;
}
带默认形参值的函数
函数声明或者定义的时候,可以给形参赋一些默认值
调用函数时,若没有给出实参,则按指定的默认值进行工作
#include <iostream>
using namespace std;
int fun(int a,int b=4)
{
int c=a+b;
return c;
}
int main()
{
cout<<fun(1)<<endl; //1 将自动匹配到a中
return 0;
}
函数重载
*相同的作用域,如果两个函数名称相同,而参数不同,我们把他们称为重载overload
*函数重载又称为函数的多态性
*函数重载不同形式
形参数量不同
形参类型不同
形参顺序不同
形参数量和形参类型都不同
*调用重载函数时,编译器通过检查实际参数的个数,类型和顺序来确定相应的被调用函数、
合法的重载例子:
int abs(int i);
long abs(long I)
double abs(double d)
非合法的重载:
int abs(int i);
long abs(int i);
void abs(int i);
//如果返回值类型不同而函数名相同,参数也相同,则是不合法的,编译器会报“语法错误”;
#include <iostream>
using namespace std;
void fun(int a,int b) //函数名称相同,类型不同(函数重载)
{
cout<<"int fun"<<endl;
}
void fun(double a,double b)
{
cout<<"double fun"<<endl;
}
// extern "C" void fun(double a,double b); 提示fun函数错误,因为加入extern "C"不进行名字改编,不构成重载(extern "C"可以实现c、c++混合编程)
int main()
{
fun(3,4);
fun(4.0,6.8);
return 0;
}
//引用是给一个变量起别名
//定义引用的一般格式
//类型 &引用名=变量名;
//在实际应用中,引用一般作为参数传递与返回值
#include <iostream>
using namespace std;
int main()
{
int bal=100;
int &ba=bal; #xa0;//引用必须初始化
cout<<ba<<endl;
ba=200; //实际上是改变bal这个变量
cout<<ba<<endl;
int bal2=500;
ba=bal2;
cout<<bal2<<endl;
cout<<ba<<endl;
cout<<bal<<endl;
return 0;
}
//const引用是指向const对象的引用
// const int ival=1024;
// const int& refVal=ival;
// int & ref2=ival;
#include <iostream>
using namespace std;
int main()
{
const int val=1024;
const int & refval=val;
// int & ref2=val #xa0;//error: cannot convert from 'const int' to 'int &'
int val2=1023;
const int& ref3=val2; //const引用可以指向非const变量
return 0;
}
//引用作为函数参数
#include <iostream>
using namespace std;
void swap(int &x,int &y) //引用作为形参
{
int temp=x;
x=y;
y=temp;
}
int main()
{
int a=5;
int b=6;
swap(a,b); //在函数调用时,引用被初始化 x=a,y=b
cout<<"a="<<a<<" #xa0;b="<<b<<endl; //结果:a=6,b=5
return 0;
}
内联函数---inline
为了协调好效率和可读性之间的矛盾,C++提供了另一种方法,即定义内联函数,方法是在定义函数时用修饰词inline。
inline int max(int a, int b)
{
return a > b ? a : b;
}
#define MAX(a, b) (a) > (b) ? (a) : (b)
内联函数与带参数宏区别
内联函数调用时,要求“实参”和“形参”的“类型一致”,另外内联函数会先对实参表达式进行求值,然后传递给形参;而宏调用时只用实参简单地替换形参。
内联函数是在编译的时候、在调用的地方将代码展开的,而宏则是在预处理时进行替换的
在C++中建议采用inline函数来替换带参数的宏。
const_cast类型转换运算符
用来移除对象的常量性(cast away the constness)
const_cast一般用于指针或者引用
使用const_cast去除const限定的目的不是为了修改它的内容
使用const_cast去除const限定,通常是为了函数能够接受这个实际参数
#include <iostream>
using namespace std;
int main()
{
const int val=100;
// int n= const_cast<int>(val); // cannot convert from 'const int' to 'int'
int n=val; //OK
/********************************************************************/
// int *p=&val; // cannot convert from 'const int *' to 'int *'
int *p=const_cast<int*>(&val); //指针p并没有指向val,p的地址和val不一样,const_cast只是移除了val的常量性
*p=200;
cout<<"*p="<<*p<<endl;
cout<<"&p="<<&p<<endl;
cout<<"val="<<val<<endl; //修改p的值,val不受影响
cout<<"&val="<<&val<<endl;
/********************************************************************/
const int val2=200;
//int & refval2=val2; // cannot convert from 'const int' to 'int &'
int& refval2=const_cast<int&>(val2); //同上,会创建临时对象空间
refval2=300; //对引用所做的改动,不会改变常量的内容
return 0;
}
#include <iostream>
using namespace std;
// const_cast 一般用来说明指针或者引用
// const_cast 不是为了修改所指向的内容
//canst_cast 去除const限定,通常是为了函数能够接受这个实际参数
const_cast 函数中作用
void fun(int &val)
{
cout<<"fun "<<val<<endl;
}
int main()
{
const int val2=200;
fun(const_cast<int&>(val2)); //去除常量性
return 0;
}
static_cast类型转换运算符
编译器隐式执行的任何类型转换都可以由static_cast完成
当一个较大的算术类型赋值给较小的类型时,可以用static_cast进行强制转换。
可以将void*指针转换为某一类型的指针
可以将基类指针指向派生类指针
无法将const转化为nonconst,这个只有const_cast才可以办得到
// static_cast
//编译器隐式执行的任何类型转换都可以由static_cast完成
//当一个较大的算术类型赋值给一个较小的类型时,可以用static_cast进行强制转换
//可以将void* 指针转换为某一类型的指针。
//可以将基类指针指向派生类指针
//无法将const转换为nonconst,这个只有const_cast才可以办得到
// 隐式转换 ---> 编译器自动完成,比如: int a, short b; a=b;
// 显示转换 ---> 强制转换
#include <iostream>
using namespace std;
int main()
{
int n=static_cast<int>(2.14);//将浮点型强制转换为int型
cout<<n<<endl;
/*************************************************************************/
double i=5.4;
void* p=&i; //将无类型指针转换为double型
double* p2=static_cast<double*>(p);
cout<<*p2<<endl;
return 0;
}
从c到c++
最新推荐文章于 2024-04-11 20:07:49 发布