【C/C++学院】0825-类模板/final_override/类模板与普通类的派生类模板虚函数抽象模板类/类模板友元/位运算算法以及类声明/Rtti 实时类型检测/高级new创建/类以及函数包装器

来源:互联网 发布:lua ide vscode 编辑:程序博客网 时间:2024/05/22 04:25

类模板

类模板多个类型默认类型简单数组模板

#pragma oncetemplate <class  T=int>//类模板可以有一个默认的值class myArray{public:myArray();~myArray();};#include "myArray.h"template <class  T=int>//每一个函数都需要加上一个默认的值myArray<T>::myArray()   //类模板成员函数在外部,需要加载类型初始化{std::cout << "构造" << typeid(T).name() << std::endl;}template <class  T=int>myArray<T>::~myArray(){std::cout << "销毁" << typeid(T).name() << std::endl;}#include <iostream>#include <array>#include <string>#include "myArray.h"#include "myArray.cpp"//类模板的成员函数没有实例化,不会自动找到,需要手动包含using namespace std;void main2(){//myArray<int>   my1;myArray<>  my2;//C++11的新功能std::cin.get();}void main1(){array<string, 5>strarray = {"calc","mspaint","notepad","tasklist","pause"};for (int i = 0; i < strarray.size();i++){std::cout << strarray[i].c_str() << std::endl;}std::cin.get();}
#include<iostream>#include<string>//定义两种数据类型的类模板//STL  数据结构,算法,适用任何类型template<class T1,class T2>class myclass{public:T1 t11;T2 t22;myclass(T1 t111, T2 t222) :t11(t111), t22(t222){}void print(){std::cout << t11 << "  "<<t22 << std::endl;}};using namespace std;void main1(){myclass<int, double> my1(10, 20.8);my1.print();myclass<double, string>my2(20.8, "123456abc");my2.print();std::cin.get();}

类模板当作函数参数

#pragma oncetemplate<class T,int n>class Array{public:Array();Array(int length);~Array();int size();T get(int num);T& operator [](int num);//重载【】void set(T data, int  num);public:T *pt;//int n;//长度};#include "Array.h"template<class T, int n>//int n不可以修改,不是类的内部成员Array<T,n>::Array(){//this->pt = nullptr;//空指针//this->n = 0;this->pt = new T[n];}template<class T, int n>//每一个函数都必须模板Array<T,n>::Array(int length){this->pt = new T[length];//n = length;}template<class T, int n>//每一个函数都必须模板Array<T,n>::~Array(){//n = 0;delete[] this->pt;}template<class T, int n>//每一个函数都必须模板int  Array<T,n>::size(){return n;}template<class T, int n>//每一个函数都必须模板T Array<T,n>::get(int num)//num是数组的下标{if (num >= n ||num <0)//报错{//异常}else{return *(this->pt + num);}}template<class T, int n>//每一个函数都必须模板void Array<T,n>::set(T data, int  num){if (num<0 || num>=n){} else{*(pt + num) = data;}}template<class T, int n>//每一个函数都必须模板T& Array<T, n>::operator [](int num){if (num < 0 || num>=n){}else{return  *(pt + num);}}#include <iostream>#include <string>#include "Array.h"#include"Array.cpp"using namespace std;void main1(){/*string str = "calc";Array<string> myarray(5);//构造五个元素数组for (int i = 0; i < myarray.size();i++){str += "X";myarray.set(str, i);std::cout << myarray.get(i) << std::endl;}*/std::cin.get();}void main22(){Array<int,5 > myarray;for (int i = 0; i < myarray.size(); i++){myarray.set(i, i);std::cout << myarray[i] << std::endl;}std::cin.get();}template<class T, int n>//类模板作为参数,类型无比明确void print(Array<T,n> &myarray){for (int i = 0; i < myarray.size();i++){std::cout << myarray[i] << std::endl;}}void main(){Array<int, 5 > myarray;for (int i = 0; i < myarray.size(); i++){myarray.set(i, i);}print(myarray);std::cin.get();}

final_override

#include<iostream>//C++11  final  override针对虚函数//final拒绝重载,某些情况下,接口拒绝被重写//加了final关键字的虚函数,无法被重写,预留接口//override,警示符,声明我重写父类的方法,父类没有接口,会提示出错class ye{public://final”函数必须是虚函数virtual void print() final  //虚函数无法重写{std::cout << "爷爷\n";}virtual void run(){std::cout << "爷爷run\n";}};class  ba:public ye{public://警示作用,强调我覆盖了父类的方法,必须是虚函数void runa () override {std::cout << "爸爸run\n";}};void main1(){ba ba1;ba1.run();std::cin.get();}

类模板与普通类的派生类模板虚函数抽象模板类

#include <iostream>#include <string>//模板类之间继承//类模板可以直接继承类模板,类型必须传递//普通类继承类模板,需要明确类型实例化类模板//类模板继承普通类,常规的操作方式//类模板当作普通哦类,需要模板参数对类进行实例化template<class T>  //抽象模板类class myclass{public:T  x;myclass(T t) :x(t){}//virtual void print()//{//std::cout << x << std::endl;//}virtual  void print() = 0;};template<class T>class newclass :public myclass<T>  //继承必须明确类型{public:T y;newclass(T t1, T t2) :myclass(t1), y(t2){}void print(){std::cout << x <<"     " <<y<< std::endl;}};void main(){myclass<int >  *p=new newclass<int>(10,9);p->print();std::cin.get();}void mainyz(){myclass<int> *p = new newclass<int>(10,9);p->print();std::cin.get();}void main1(){//newclass<double> my1(10.9, 2.3);//my1.print();newclass<std::string> my1("abc", "xyz");my1.print();std::cin.get();}class xyz{public:int x;int y;int z;xyz(int a, int b, int c) :x(a), y(b), z(c){}void  print(){std::cout << x << y << z;}};template<class T>class  newxyz :public xyz{public:T a;newxyz(T t1,int a1,int b1,int c1) :xyz(a1,b1,c1),a(t1){}void print(){std::cout << "Ta=" << a << std::endl;std::cout << x << y << z << std::endl;}};class classrun:public newxyz<int >{public:int d = 1000;classrun(int a2, int b2, int c2, int d2) :newxyz<int>(a2,b2,c2,d2){}void print(){std::cout << d << x << y << z << a;}};void mainy(){classrun  run1(1, 2, 3, 4);run1.print();std::cin.get();}void mainx(){std::string  str1 = "china";newxyz<std::string> new1(str1,10,90,89);new1.print();std::cin.get();}

类模板友元

#include <iostream>#include <string>#include <vector>template<class T> class myclass;template<class T> void print(myclass<T> & my, T t1);template<class T> class myclass{public://friend  void print(myclass<T> & my, T t1);//友元函数放在模板类的内部,实现重载friend void print(myclass<T> & my, T t1);friend  myclass  *  operator+(const myclass<T> & my1,const myclass<T> &my2){//myclass class1  栈,用完了马上释放//堆上申请一个myclass * p = new myclass(my1.x + my2.x, my1.y + my2.y);return p;}myclass(T t1, T t2) :x(t1), y(t2){}//访问私有需要友元,private:T  x;T  y;};template<class T>void print(myclass<T> & my, T t1){std::cout << typeid(t1).name() << std::endl;std::cout << my.x << "   " << my.y << std::endl;}using namespace  std;void main1(){myclass<int> my1(19, 29);vector<int >  v1;vector<vector<int >  >  v2;vector<vector<vector<int > > >  v3;using VEC = vector<vector<vector<int > > >;//C++11简写VEC v4;//等价于三维int类型数据,模板}void main(){myclass<int> my1(19, 29);myclass<int> my2(11, 1);print(my1, 10);//printA(my1);myclass<int> *pclass = my1 + my2;print(*pclass,10);std::cin.get();}

位运算算法以及类声明

不是用+号,实现加法

#include <iostream>//加减乘除,都是靠位运算,//将来从事手机端,嵌入式开发,位操作,class jia;//声明,只能声明指针或者引用jia  *pjia1;jia *& pjia2=pjia1;//jia & jia2;//jia jia1;class jia{public:jia(int a, int b) :x(a), y(b){     }int jiafa(){return x + y;}int getx(){return x;}int gety(){return y;}int newjiafa(int a, int b){if (a == 0){return b;}else if (b == 0){return a;}else{int res = a^b;//先求结果int wei = (a&b) << 1;//进位,左移,乘以2,//a+b=a^b+(a&b)<<1;std::cout << "res=" << res << " " << "wei=" << wei << "\n";return newjiafa(res, wei);}}private:int x;int y;};int newjiafa(int a,int b){if (a == 0){return b;}else if (b==0){return a;//让相与慢慢趋势于0}else{int res = a^b;//先求结果int wei = (a&b) << 1;//进位,左移,乘以2,//a+b=a^b+(a&b)<<1;//表达式std::cout << "res=" << res << " " << "wei=" << wei << "\n";return newjiafa(res, wei);}}void main1(){//std::cout << newjiafa(11, 22) << std::endl;jia  jia1(10, 9);std::cout << jia1.jiafa() << std::endl;std::cout << jia1.newjiafa(jia1.getx(), jia1.gety()) << std::endl;std::cin.get();}void main2(){int num;std::cin >> num;int i = 0;while (num){i++;num &= num - 1;//让数据趋向于0}std::cout << i << std::endl;std::cin.get();std::cin.get();}int get1(int num){int count = 0;//表示位数unsigned int  flag = 1;//0000001  flag                       //   1111  num                                             //0000001      1                       //flag  000001                      //num      1111                                      //flag   0000010                      //num      1111                             //  0000010                    //flag   0000100                     //num      1111                   //  00000100                   //flag   0001000                   //num       1111                                        //  000001000                       //flag   00010000                        //num       1111                                  //0                  while (flag){std::cout << num << "  " << flag << std::endl;if (num & flag) //不为0就自增{count++;}flag = flag << 1;}return count;}void main(){int num;std::cin >> num;int i = 0;i = get1(num);std::cout << i << std::endl;std::cin.get();std::cin.get();}

类模板与友元函数友元类

类模板与友元函数

#include<iostream>template <class T> class myclass;template <class T> void printA(myclass<T> my);template <class T>class myclass{public:myclass(T t) :x(t){}friend void print(myclass<T> my){std::cout << my.x << std::endl;}friend void printA<T>(myclass<T> my);//友元函数如果在外部,第一声明要加类型T//必须要声明类还有函数private:T x;  //模板友元类//int y;访问与T无关的类型,普通友元类};template <class T>void printA(myclass<T> my){std::cout << my.x << std::endl;}void mainA(){myclass<int> my1(10);myclass<double> my2(10.9);printA(my1);print(my2);std::cin.get();}

类模板与友元类

#include<iostream>template <class T> class myclass;template<class T> class runclass;////友元类必须声明类的存在,//需要声明友元类,必须要与类型相关template <class T>class myclass{public:myclass(T t) :x(t){}friend class runclass<T>;//声明友元类private:T x;  //模板友元类//int y;访问与T无关的类型,普通友元类};template<class T>class runclass{public:void print(const myclass<T> & my){std::cout << my.x << std::endl;}};void main(){myclass<double> my1(19.8);runclass<double> run1;run1.print(my1);std::cin.get();}

类模板当作类模板参数

#include<iostream>#include<string>using namespace  std;//类模板当作一个类的参数//设计STL时候用到//面试,类模板当作参数template<class T>class ren      //一个通用的类的类模板{public:T name;ren(T t) :name(t){}};template< template<class T> class T1 >  //使用类模板当作模板参数的类class people{public:T1<string> t1x="123123";//T1必须实例化 。必须结合T1<string>  num = "ABC"; //等价于ren类型//T1 x;people(T1<string> &t1) {std::cout << typeid(t1).name() << std::endl;std::cout << typeid(T1).name() << std::endl;std::cout << t1.name << std::endl;t1x = t1;num = t1;}};void main(){ren<string> ren1("hello8848"); //基本数据类型people<ren> people1(ren1);//嵌套的类模板//std::cout << people1.t1x.name << std::endl;//std::cout << people1.num.name << std::endl;//std::cout << people1.str << std::endl;std::cout << people1.t1x.name << std::endl;std::cout << people1.num.name << std::endl;std::cout << ren1.name << std::endl;std::cin.get();}

static与类模板

#include <iostream>#include<string>//类模板的static成员,对象,类名《类型》//不同类型的静态成员变量,地址不一样//相同类型的静态成员变量,地址一样template<class T>class myclass{static int data;public:static int num;//声明T a;myclass(T t) :a(t){num++;data++;}static void run(){//this->a;std::cout << data << std::endl;std::cout << typeid(T).name() << "\n";}};template<class T>int  myclass<T>::num = 0;template<class T>int  myclass<T>::data = 0;//静态变量,静态函数,同类,共享的//类型不同,不是共享void main(){myclass<int > my1(10);myclass<double > my2(10.9);myclass<int > my4(10);myclass<int>::run();myclass<int>::run();myclass<int>::run();my1.run();myclass<double>::run();//myclass<int>::data;std::cin.get();}void mainA(){myclass<int > my1(10);myclass<double > my2(10.9);myclass<std::string > my3("1234");myclass<int > my4(10);std::cout << &my1.num << std::endl;std::cout << &my2.num << std::endl;std::cout << &my3.num << std::endl;std::cout <<&my4.num << std::endl;std::cout << &myclass<int >::num << std::endl;std::cout << &myclass<float >::num << std::endl;std::cin.get();}

类嵌套以及类模板嵌套

类嵌套

#include <iostream>//类的嵌套class myclass{public:class newclass{public:int num;}new1;};class newnewclass :public myclass{};void main2(){newnewclass newx;newx.myclass::new1.num=10;   std::cout << newx.new1.num;std::cin.get();}void main1(){myclass myclass1;myclass1.new1.num = 19;std::cout << myclass1.new1.num;std::cin.get();}

类模板嵌套

#include<iostream>template<class T>class myclass{public:class newclass{public:int num;}new1;//定义的方式newclass new2;template<class V>class  runclass{public:V v1;};//类模板后面不可以直接初始化runclass<T> t1;runclass<double> t2;};void main(){myclass<int > my1;my1.new1.num = 10;my1.t1.v1 = 12;my1.t2.v1 = 12.9;std::cout << my1.t1.v1 << "\n" << my1.t2.v1;std::cin.get();}

Rtti 实时类型检测

#include <iostream>//rtti,实时类类型检测,//typeid,  dynamic_cast必须依赖于虚函数表//类型不匹配转换失败,返回为空。类型安全//成员变量的覆盖//虚函数有虚函数表确定数据类型class A{public:int num;static int data;   virtual  void run(){std::cout << "Arun\n";}};int A::data=1;class B:public A{ public: int num=0; static int data; void run() { std::cout << "Brun\n"; } void test() { std::cout << num<<"\n"; std::cout << "Btest\n"; }};int B::data = 2;void main(){A a1;B b1;A *p1 = &a1;A *p2 = &b1;B *p3(nullptr);//p3 = static_cast<B *>(p1);//直接赋地址,不安全,与虚函数无关p3 = reinterpret_cast<B*>(p2);std::cout << p3 << "\n";p3->test();std::cin.get();}void main3(){A a1;B b1;A *p1 = &a1;A *p2 = &b1;B *p3(nullptr);//p3 = dynamic_cast<B*>(p2);//dynamic必须要有虚函数,根据虚函数表转换,不能转换//转换失败为空//类的空指针可以调用不调用数据的函数//转换成功就是地址std::cout << p3 << "\n";p3->test();std::cin.get();}void main2(){//A *p1 = new A;//A *p2 = new B;A a1;B b1;A *p1 = &a1;A *p2 = &b1;std::cout << typeid(p1).name() <<"  "<< typeid(p2).name() << std::endl;std::cout <<( typeid(p1) == typeid(p2))<<"\n";std::cout << typeid(*p1).name() << "  " << typeid(*p2).name() << std::endl;std::cout << (typeid(*p1) == typeid(*p2)) << "\n";//重载的方式判定类型是否一致std::cin.get();}void main1(){B b1;b1.num = 10;//覆盖现象b1.A::num = 20;std::cout << b1.num << "\n" << b1.A::num<< std::endl;std::cout << b1.data <<"   "<< b1.A::data << "\n";std::cout << &b1.data << "   " << &b1.A::data << "\n";std::cin.get();}

高级new创建

#include <iostream>class myclass{public:myclass(){std::cout << "创建\n";}~myclass(){std::cout << "销毁\n";}};void main(){char *pcathe = new char[1024];char *pcatheend = pcathe + 1024;std::cout <<(void*) pcathe << "   " << (void*)pcatheend << std::endl;myclass *p = new(pcathe)myclass[10];//限定区域分配内存,覆盖模式std::cout << p << std::endl;//delete[] p;一般不需要delete.自动覆盖std::cout << p << std::endl;    p = new(pcathe)myclass[10];std::cout << p << std::endl;//delete[] p;//只能释放一次std::cout << p << std::endl;/*myclass *pclass = new  myclass[10];std::cout << pclass << std::endl;delete []pclass;pclass = NULL;std::cout << pclass << std::endl;pclass = new  myclass[10];std::cout << pclass << std::endl;delete [] pclass;std::cout << pclass << std::endl;*/std::cin.get();}

类以及函数包装器

#include<iostream>template<typename T,typename F>T run(T t, F f) //包装器,实现一个操作接口,操作多个类的方法{ return  f(t);}int add(int num){return num + 10;}class myclass{public:int  num;myclass(int data) :num(data){}int operator ()(int X){return X*num;}};class myclassA{public:int  num;myclassA(int data) :num(data){}int operator ()(int X){std::cout << "A\n";return X-num;}};void main(){myclass my1(5);std::cout << run(101,my1) << std::endl;std::cout << run(101, myclassA(51)) << std::endl;std::cin.get();}void main1(){auto  num = 100;auto  func = add;std::cout << run(num, add) << std::endl;std::cin.get();}

类成员函数指针

C函数指针

#include<stdio.h>int addC(int a, int b){return a + b;}void  run(){printf("\nrun");}void main1(){int(*p)(int, int) = addC;void(*p1)() = run;printf("%d\n", p(1, 2));printf("%d\n", (*p)(1, 2)); //*p编译器自动将*p解释为pprintf("%d\n", (**********p)(1, 2)); //*p编译器自动将*p解释为pprintf("%d\n", (&(**p))(1, 2)); //&没有*不可以执行,超过两个地址就不可以//&p不能,//printf("%d\n", (&(p))(1, 2));printf("%p,%p,%p", &p, *p, p);printf("\n%p,%p,%p", &p1, *p1, p1);//printf("%d\n", (&p)(1, 2));//取地址,取就是CPU即将调用函数执行,C语言内嵌ASM//老版本,*p,p,&pgetchar();}

Cpp函数指针

#include <stdio.h>#include<iostream>void add(int a, int b){std::cout << a + b << std::endl;}void mainA(){void(*p)(int, int) = add;p(1, 2);(*p)(1, 2);//函数指针,会被当作指针来处理,*p与p效果一样(**************p)(1, 2);//函数指针,会被当作指针来处理,*p与p效果一样(*&p)(1, 2);(*******&p)(1, 2);std::cout << (void *)p << "  " << (void *)(*p) << std::endl;std::cout << typeid(p).name() << std::endl;std::cout << typeid(*p).name() << std::endl;std::cout << typeid(&p).name() << std::endl;std::cout << typeid(*&p).name() << std::endl;//C++编译器会自动将*p处理为p//std::cin.get();}

类成员函数指针数组

#include<iostream>#include<stdio.h>//类成员函数指针,类成员函数指针数组,类成员二级函数指针class com{private:int a;int b;public:com(int x, int y) :a(x), b(y){}int  jia(int a, int b){return a + b;}int  jian(int a, int b){return a - b;}int  cheng(int a, int b){return a * b;}int  chu(int a, int b){return a / b;}};void main1x(){com com1(100, 20);auto fun1 = &com::jia;int(com::*p)(int, int) = &com::jia;std::cout << (com1.*p)(10, 20) << std::endl;//引用对象,类成员函数指针std::cout << typeid(p).name() << std::endl;std::cout << typeid(fun1).name() << std::endl;std::cin.get();}typedef int(com::*P)(int, int);void main(){com com1(100, 20);//P fun1[4] = { &com::jia, &com::jian, &com::cheng, &com::chu };//类成员函数指针数组int(com::*fun1[4])(int, int) = { &com::jia, &com::jian, &com::cheng, &com::chu };for (int i = 0; i < 4; i++){std::cout << (com1.*fun1[i])(10, 20) << std::endl;}int(com::**funp)(int, int) = fun1;//指向类成员函数指针的指针for (; funp < fun1 + 4; funp++){std::cout << (com1.**funp)(10, 20) << std::endl;printf("%p", *funp);}for (int i = 0; i < 4; i++) {auto func = fun1[i];std::cout << typeid(func).name() << std::endl;printf("%p", func);     }std::cin.get();}


0 0
原创粉丝点击