您的位置:首页 > 编程语言 > C语言/C++

C++构造,析构,友元类,对象,static成员,复制构造函数,运算符重载杂谈

2014-12-25 00:43 543 查看
1.

构造函数初始化分配内存

析构函数清空数据,释放内存

#include<stdlib.h>
#include<iostream>

class create
{
int *p;
public:
create(int n)//析构函数初始化分配内存
{
p = new int
;
for (int i = 0; i != n; i++)
{
p[i] = i;
std::cout << p[i] << std::endl;
}
}
~create()//析构函数清空数据,释放内存
{
delete[]p;
}
};
void main()
{

create K(16);
system("pause");

}


#include<iostream>
class circle
{
public:
double R;
public:
circle(double r)//默认空构造函数但如果定义了构造函数,必须使用这个构造函数
{
R = r;
}
public:
void setR(double r)
{
R = r;
}
double area()
{
return R*R*3.1415;
}

};
void maian()
{
int a = 5;
int b(5);
std::cout << a << std::endl;
std::cout << b << std::endl;
system("pause");

}

void mainfasasd()
{
/*circle A;无构造函数或者构造函数默认为空
A.setR(10);
std::cout << A.area() << std::endl;
system("pause");*/
circle B(100); //调用构造函数 也是初始化一个B的对象,必须这样做
std::cout << B.area()<< std::endl;
system("pause");

}


2.
友元类

友元类的所有成员函数都是另一个类的友元函数,都可以访问另一个类中的隐藏信息(包括私有成员和保护成员)。

include<iostream>

class A
{
friend class B;//与B可以共用a的函数和数据
private:
int x;
public:
void printx()
{
std::cout << x << std::endl;
}
};
class B
{
private:
A obj;//创建一个A类的对象
public:
void setx(int a)
{
obj.x = a;
obj.printx();
}
};

int mai111111n()
{

//A A1;
//A1.printx();
B b;
b.setx(100);

system("pause");
return 0;
}


3.友元函数

友元函数是指某些虽然不是类成员却能够访问类的所有成员的函数。类授予它的友元特别的访问权。通常同一个开发者会出于技术和非技术的原因,控制类的友元和成员函数(否则当你想更新你的类时,还要征得其它部分的拥有者的同意)。

#include<iostream>
class OO
{
friend void fun(OO *p, int a);//声明友元函数,
friend void funA(OO&OOA, int a);//声明了友元函数,这个函数可以访问私有
int x;
public:
void printx(int a)
{
x = a;
std::cout << x << std::endl;
}
};
//注意友元函数无this指针
void fun(OO *p, int a)
{
p->x = a;//访问private成员
std::cout << p->x<< std::endl;
}
void funA(OO&OOA, int a)
{
OOA.x = a;//友元函数访问private成员
std::cout << OOA.x<< std::endl;
}
void main()
{
OO OO1;
OO1.printx(100);
fun(&OO1, 1002);
funA(OO1, 1000);
system("pause");
}


对象的创建

include<iostream>

class M
{
int a, b;
public:
M(int x, int y)
{
a = x;
b = y;
}
void seta(int x)
{
a = x;
std::cout << a << std::endl;
}
void setb(int y)const  //强调不可以修改类的内部成员变量
{
//b = y;无法修改  const限定了
std::cout << b << std::endl;
}
};

void ma1111in()
{

M text(2, 4);
text.seta(1);

system("pause");

}


Static成员

#include<iostream>

class simple
{
int x, y;
static const int z =1;
static int u;//在外部初始化
public:
simple(int a, int b, int c)
{
x = a;
y = b;
this->u = c;

}
void printu()
{
std::cout << this->u << std::endl;
}
static void printAB()//静态,不依赖与对象,可以直接运行
{
std::cout << "asdfasf" << std::endl;
}
};
int simple::u(10);//外部初始化
void main()
{
simple A(1, 2, 3);
A.printu();
A.printAB();
system("pause");
//simple::printu();不合法,合法,依赖对象
simple::printAB();//合法,不依赖与对象,可以直接运行
system("pause");
}


复制构造函数

拷贝构造函数,是一种特殊的构造函数,它由编译器调用来完成一些基于同一类的其他对象的构建及初始化。其唯一的形参必须是引用,但并不限制为const,一般普遍的会加上const限制。此函数经常用在函数调用时用户定义类型的值传递及返回。拷贝构造函数要调用基类的拷贝构造函数和成员函数。如果可以的话,它将用常量方式调用,另外,也可以用非常量方式调用。

一般格式 类名(const 类名 &s)//

通过已经存在的对象来初始化自己

Const限定传入的参数在复制构造函数不被修改

#include<stdlib.h>
#include<iostream>
class TTTT
{
int a;
public:
TTTT(int x)
{
a = x;
std::cout << a << std::endl;
}
TTTT(const TTTT &s)//通过已经存在的对象,初始化自己
{  //限定s这个时候不可以修改
a = s.a;
std::cout << a << std::endl;
}
};
void ma11111in()
{

TTTT A1(6);
TTTT A2(A1);
system("pause");
}


浅复制与深复制区别

浅复制(浅克隆)

被复制对象的所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用仍然指向原来的对象。换言之,浅复制仅仅复制所考虑的对象,而不复制它所引用的对象。

深复制(深克隆)

被复制对象的所有变量都含有与原来的对象相同的值,除去那些引用其他对象的变量。那些引用其他对象的变量将指向被复制过的新对象,而不再是原有的那些被引用的对象。换言之,深复制把要复制的对象所引用的对象都复制了一遍。

简单的说就是
//浅复制是直接复制指针的地址,共用一段内存
//深复制,就是各自用各值得内存
#define _CRT_SECURE_NO_WARNINGS
#include<iostream>
#include<string>
//深拷贝就是除了一般复制,还保存内存复制
//浅拷贝就是一般复制,只指针复制,这样会使2个对象的指针指向同一片内存区域
class name
{
public:
name(char *pn);//成员函数申明
~name();//析构函数声明
name(const name &obj);//复制析构函数声明
void printname()
{
std::cout << pname << std::endl;
}
private:
char *pname;
int size;
};
name::name(char *pn)
{
std::cout << "构造函数创建" << std::endl;
pname = new char[strlen(pn) + 1];
if (pname != 0)
{
strcpy(pname, pn);
size = strlen(pn);
}
}
name ::~name()
{
std::cout << "销毁" << pname << std::endl;
pname[0] = '\0';
delete[]pname;
size = 0;
}
name::name(const name &obj)
{
pname = new char[strlen(obj.pname) + 1];
if (pname != NULL)
{
strcpy(pname, obj.pname);
}
size = obj.size;
//上面是深复制
//浅复制则是 pname=obj.pname指向同一内存地址
}

void main()
{
name obj1("abcd");
obj1.printname();
name obj2(obj1);
obj2.printname();
system("pause");
}


简单运算符重载

#include<iostream>
//x+yi  复数++,--
class fushu
{
private:
int x;
int y;
public:
fushu()
{

}
fushu(int a, int b)//构造函数
{
x = a;
y = b;
}
void printfushu()
{
std::cout << x << "+" << y << "i" << std::endl;
}
fushu operator ++()
{
x++;
y++;
return *this;//返回自己
}
fushu operator --()
{
x--;
y--;
return *this;
}
fushu operator =(fushu b)
{
x = b.x;
y = b.y;
return *this;
}
~fushu()
{

}
fushu operator +(fushu a)//实现复数加法
{
fushu temp(0, 0);
temp.x = x + a.x;
temp.y = y + a.y;
return temp;
}
fushu operator()()
{

}
};

int mai11111n()//main函数无法重载
{
fushu A(3, 5);
A.printfushu();
A++;//重载
A.printfushu();

A--;//重载
A.printfushu();
fushu B;
B = A;//重载
B.printfushu();
A = A + B;
A.printfushu();

system("pause");
return 0;
}
例子2
#include<iostream>

class sanwei
{
private:
int x;
int y;
int z;
public:
sanwei(int a = 0,int b=0,int c=0)
{
x = a;
y = b;
z = c;

}
sanwei operator =(sanwei X)
{
this->x = X.x;
this->y = X.y;
this->z = X.z;
return *this;
}
sanwei operator ++()
{
this->x++;
this->y++;
this->z++;
return *this;
}
sanwei operator+(sanwei X)
{
sanwei temp;
temp.x= this->x + X.x;
temp.y = this->y + X.y;
temp.z = this->z + X.z;
return temp;
}
void show()
{
std::cout << "x=" << x << " " << "y=" << y << " " << "z=" << z << std::endl;
}
void assign(int a, int b, int c)
{
x = a;
y = b;
z = c;
}
};
void maiafadfaAn()
{
sanwei A(1,2,3);
sanwei B;
sanwei C;
A.show();
B.show();
C.show();
B++;
B++;
B.show();
C = A + B;
C.show();
C.assign(1, 2, 3);
C.show();
system("pause");

}
void mainkkk()
{
sanwei A(1,2,3);
sanwei B;
B = A;
A.show();
B.show();
A = A + B;
A.show();
A++;
A.show();

system("pause");

}<span style="color:#57a64a;">
</span>


友元函数实现重载(友元函无this指针)

#include<iostream>

class fushuA
{
friend fushuA operator -(fushuA & U, fushuA &V);//友元函数声明
private:
int x, y;
public:

fushuA(int a=0, int b=0)//构造函数
{
x = a;
y = b;
}
fushuA operator+(fushuA a)//重载运算符
{
fushuA temp(0, 0);
temp.x = x + a.x;
temp.y = y;
return temp;
}
fushuA operator =(fushuA b);//=函数实现声明
void show()
{
std::cout << "x=" << x << "   " << "y=" << y<< std::endl;
}
~fushuA()
{

}
fushuA operator ++()//前置  ++M调用这个
{
this->x++;
this->y++;
return *this;
}
fushuA operator ++(int a)//后置 M++调用这个
{
this->x++; x++;
this->y++;
return *this;
}
fushuA operator[] (fushuA *a)  //[]实现重载
{
std::cout << a->x << a->y << std::endl;
return *this;
}
};
fushuA operator -(fushuA &U, fushuA &V)//友元函数实现运算符重载,因为友元函数木有this指针
{
fushuA C;
C.x = U.x - V.x;
C.y = U.y - V.y;
return C;
}
fushuA fushuA::operator =(fushuA b)//成员函数重载  移到外部
{
x = b.x;
y = b.y;
return *this;
}

void main()
{
/*fushuA A(1, 9);
fushuA B(3, 19);
fushuA D;
fushuA C;
C = B+ A;//自己重载的运算符遵循自己的规则
//	A.show();
C.show();
D = A+ B;
D.show();//与c.show不同,不满足交换律是因为自己的规则
fushuA E = D - C;
E.show();*/
fushuA M(10, 20);
fushuA N;
//N = M++;//指行的是  fushuA operator ++(int a)
//N.show();
N = ++M;//执行的是 fushuA operator ++()
N.show();

fushuA O(15, 25);
O[&O];//[]实现重载

system("pause");

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐