参考:
重点:
1.成员函数指针
###正文:
//达内C++教程\03_标准C++编程_陈宗权_7day\标准C++编程_day01PM_常量_指针_new_delete_函数
#include<iostream>
#include<cstdlib>// C++,把.h改为c
//#include<stdlib.h>//C
#include<string>
using namespace std;
struct date {
int year;
int month;
int day;
void print() { std::cout <<year<<"-"<<month<<"-"<<day << std::endl; }
};
void f(double d) { std::cout << d << std::endl; }
//形参 void写与不写等价
void f1() { std::cout <<"hello" << std::endl; }
void f2(void) {}
void f2(double) {}//有类型无名字:哑元,为了新旧兼容
// date里int成员的地址int date::*p
// 结构变量.*成员指针,结构指针->*成员指针
void showmember(date a[], int n, int date::*p)
{
for (int i = 0; i < n; i++) {
//std::cout << a[i].*p << " ";
//std::cout << *(a+i).*p << " ";
std::cout << (a + i)->*p << " ";
}
}
int main() {
double d = 123.15;
//E的地址不能修改
double* const E = &d;
std::cout <<*E << std::endl;
//////////////////////////////////////////////////////////
// C++会优化,对于常量的访问,不会直接去内存取数据,而C不会
// 自己的代码写的不能改,但是自己改,这是不合理的。
const int n = 100;
// volatile:从内存里取数据
volatile const int m = 200;
int *p = (int*)&n;
*p = 123;
p = (int*)&m;
*p = 456;
std::cout <<"n: "<< n <<",m: "<< m << std::endl;
///////////////////////////////////////////////////////////
//static_cast: 合理转换,数值类型之间的转换,或者指针与void*之间的转换
//const_cast: 把常量转成变量,用于临时去掉const限制,转换语句本身,出了这个语句就没了
//reinterpret_cast: 任意两种指针类型之间,指针和数值之间的转换,最危险的转换,一般不用
//dynamic_cast:以后再说
// C++ 编译可能有警告
//int n = 123.67;
int nn = static_cast<int>(12.45);
int* pp = static_cast<int*>(malloc(sizeof(int)*10));
free(pp);
// 不合理的转换,很少使用
const int k = nn;
std::cout << "before: k" << k << std::endl;
const_cast<int&>(k) = 789;
std::cout << "after: k" <<k <<std::endl;
nn = (int)12.34;
// 把类型当函数一样
nn = int(12.34);
std::cout <<"nn: "<<nn << std::endl;
//空的表示数值的0
nn = int();
std::cout << "nn: " << nn << std::endl;
//int mm = 100;
// 把初始值放在括号里,初始化一次,赋值可以多次
int mm(300);
std::cout << "mm: " << mm << std::endl;
//会被认为是函数声明
//int x();
//没必要这么写!!!!!
//int(y) =200;//int(f)类似强制类型转换
//std::cout <<"y:" <<y<< std::endl;
///////////////////////////////////////////////////////////
//new 类型 <===> (类型*)mallac(sizeof(类型));
//以下两个等同
string* ppp = static_cast<string*>(malloc(sizeof(string)));
int* qqq = new int;
//初始化999
int* rrr = new int(999);
int nnn;
nnn = 10;
//nothrow 不扔出来
//数组没有理由初始化,也没办法初始化
int *a = new (nothrow)int[nnn];
// 申请空间失败,返回的是是空指针
if (a == NULL)
{
cout <<n*sizeof(int) <<"申请空间失败";
}
else
{
//用new初始化,不初始化,不能保证是0!!!!!!!!!!!!!!!!!!!!!!!!!
for (int i = 0; i < n; i++) {
std::cout << a[i] << " ";
}
}
std::cout << "*qqq: " << *qqq<< std::endl;
//没有new 不能delete
//delete ppp;
free(ppp);
delete qqq; qqq = NULL;
delete rrr; rrr = NULL;
delete[] a; a = NULL;
//////////////////////////////////////////////////////////////////
date aaaa[5] = { {2020,1,27},{ 2021,1,27 },{ 2022,1,27 },{ 2023,1,27 },{ 2024,1,27 }};
date dddd = { 2025,1,27 };
std::cout <<"&dddd: "<< &dddd << std::endl;
std::cout << "&dddd.year: " << &dddd.year << std::endl;
std::cout << "&dddd.month: " << &dddd.month << std::endl;
std::cout << "&dddd.day: " << &dddd.day << std::endl;
//取相对地址
std::cout <<"&date::year: "<< &date::year << std::endl;
//函数地址和成员地址输出都会设置成true
std::cout << &main << std::endl;
std::cout << &f << std::endl;
//联合,共用同一块内存空间。
union {
int nnnn;
int date::*mp;
};
mp = &date::day;
//nnnn == mp,即可得到mp的地址
std::cout <<"nnnn: "<<nnnn<< std::endl;
union {
int iNum;
int* pNum2;
};
int mmmmm=2;
pNum2 = &mmmmm;
std::cout <<"iNum: "<<hex<<iNum << std::endl;
std::cout.unsetf(ios::hex);
std::cout <<"pNum2: "<<pNum2 << std::endl;
std::cout <<"pNum2 add: "<<&pNum2 << std::endl;
std::cout << "iNum add: "<<&iNum << std::endl;
// .* 当成运算符
std::cout << "dddd.*mp: " << dddd.*mp << std::endl;
mp = &date::year;
std::cout << "dddd.*mp: " << dddd.*mp << std::endl;
showmember(aaaa,5,&date::month);
showmember(aaaa, 5, &date::year);
showmember(aaaa, 5, &date::day);
dddd.print();
aaaa[3].print();
//成员函数指针
void(date::*pf)() = &date::print;
(dddd.*pf)();
((aaaa+0)->*pf)();
system("pause");
}
网友评论