Aprendizaje de objetos y clases de C ++ [parte 3: características del objeto 2.0]

Aprendizaje de objetos y clases de C ++ [parte 3: características del objeto 2.0]

Las variables miembro y las funciones miembro se almacenan por separado

En C ++, las variables miembro y las funciones miembro de una clase se almacenan por separado.
Solo las variables miembro no estáticas pertenecen a los objetos de la clase.
Hay cuatro tipos de miembros:

  • Variable miembro no estática
  • Variable miembro estática
  • Función miembro no estática
  • Función de miembro estático

El código de visualización específico es el siguiente:

// arrayone.cpp -- small arrays of integers
#include <iostream>

using namespace std;

#include <string>

class Person
{
    
    
public:
    Person()
    {
    
    
        mA = 0;
    }
    //非静态成员变量占对象空间
    int mA;
    //静态成员变量不占对象空间
    static int mB;
    //函数也不占对象空间,所有函数共享一个函数实例
    void func()
    {
    
    
        cout << "mA:" << this->mA << endl;
    }
    //静态成员函数也不占对象空间
    static void sfunc()
    {
    
    
    }
};

int main()
{
    
    
    cout << sizeof(Person) << endl;
    
    system("pause");
    return 0;
}

Cabe señalar que:
una clase vacía ocupa un byte de memoria, el propósito es distinguir las ubicaciones de memoria ocupadas por diferentes objetos vacíos.
Si contieneVariable miembro no estática, Ocupa el número de bytes de la variable miembro.
Si hay más de uno, sume.

este concepto de puntero

El puntero this apunta al objeto al que pertenece la función miembro llamada.
Este puntero es un tipo de puntero que implica todas las funciones miembro no estáticas.
No es necesario definir este puntero. Se puede usar directamente
con el propósito de este puntero:

  • Cuando el parámetro formal y la variable miembro tienen el mismo nombre, este puntero se puede utilizar para distinguir
  • Para devolver el objeto en sí en la función miembro no estática de la clase, puede usar return * this

El siguiente código es un ejemplo de cómo devolver el objeto en sí:

Person& PersonAddPerson(Person p)
	{
    
    
		this->age += p.age;
		//返回对象本身
		return *this;
	}

De esta forma, las llamadas recursivas se pueden utilizar al llamar:

p2.PersonAddPerson(p1).PersonAddPerson(p1).PersonAddPerson(p1);

Acceso de puntero nulo a funciones miembro

Podemos definir un puntero a una clase, pero dejarlo vacío (realmente no entiendo qué es esto por ahora).
Este puntero nulo puede llamar a funciones miembro, pero preste atención a si se utiliza este puntero.
El cuerpo principal del programa es el siguiente:

//空指针访问成员函数
class Person {
    
    
public:

	void ShowClassName() {
    
    
		cout << "我是Person类!" << endl;
	}

	void ShowPerson() {
    
    
		if (this == NULL) {
    
    
			return;
		}
		cout << mAge << endl;
	}

public:
	int mAge;
};

void test01()
{
    
    
	Person * p = NULL;
	p->ShowClassName(); //空指针,可以调用成员函数
	p->ShowPerson();  //但是如果成员函数中用到了this指针,就不可以了
}

int main() {
    
    

	test01();

	system("pause");

	return 0;
}

Puntos a los que prestar atención:

  • Método de definición de puntero nulo.
  • Método de función de miembro de llamada de puntero nulo.
  • Use variables miembro, no puede usar punteros nulos
  • Si ocurre la situación anterior, se deben utilizar declaraciones de juicio para aumentar la solidez del programa.

función miembro modificada const

Función constante:

  • Después de agregar const después de la función miembro, llamamos a esta función una función constante
  • Las propiedades de los miembros no se pueden modificar en funciones constantes
  • Después de agregar la palabra clave mutable en la declaración de atributo de miembro, aún se puede modificar en la función normal

Objeto regular:

  • Agregue const antes de declarar el objeto para llamar al objeto un objeto constante
  • Los objetos constantes solo pueden llamar a funciones constantes

El cuerpo principal del programa de prueba es el siguiente:

class Person {
    
    
public:
	Person() {
    
    
		m_A = 0;
		m_B = 0;
	}

	//this指针的本质是一个指针常量,指针的指向不可修改
	//如果想让指针指向的值也不可以修改,需要声明常函数
	void ShowPerson() const {
    
    
		//const Type* const pointer;
		//this = NULL; //不能修改指针的指向 Person* const this;
		//this->mA = 100; //但是this指针指向的对象的数据是可以修改的

		//const修饰成员函数,表示指针指向的内存空间的数据不能修改,除了mutable修饰的变量
		this->m_B = 100;
	}

	void MyFunc() const {
    
    
		//mA = 10000;
	}

public:
	int m_A;
	mutable int m_B; //可修改 可变的
};


//const修饰对象  常对象
void test01() {
    
    

	const Person person; //常量对象  
	cout << person.m_A << endl;
	//person.mA = 100; //常对象不能修改成员变量的值,但是可以访问
	person.m_B = 100; //但是常对象可以修改mutable修饰成员变量

	//常对象访问成员函数
	person.MyFunc(); //常对象只能调用const的函数

}

int main() {
    
    

	test01();

	system("pause");

	return 0;
}

Puntos a dominar:

  • Cómo definir objetos comunes
  • Cómo definir funciones regulares (const se coloca después del nombre de la función)
  • Los objetos constantes pueden modificar las variables miembro modificadas por mutable
  • Los objetos constantes solo pueden llamar a funciones constantes

Función global como amigo

La clave del amigo esamigo
Tipos de amigos:

  1. Función global como amigo
  2. Compañera de clases
  3. Función de miembro como amigo

Función global como amigo

Para funciones globales como amigos, el código es el siguiente:

// arrayone.cpp -- small arrays of integers
#include <iostream>

using namespace std;

#include <string>

class Building
{
    
    
    //告诉编译器 goodGay全局函数 是 Building类的好朋友,可以访问类中的私有内容
    friend void goodGay(Building *building);

public:
    Building()
    {
    
    
        this->m_SittingRoom = "客厅";
        this->m_BedRoom = "卧室";
    }

public:
    string m_SittingRoom; //客厅

private:
    string m_BedRoom; //卧室
};

void goodGay(Building *building)//这里用的是指针传递
{
    
    
    cout << "好基友正在访问: " << building->m_SittingRoom << endl;
    cout << "好基友正在访问: " << building->m_BedRoom << endl;
}

void test01()
{
    
    
    Building b;
    goodGay(&b);//传入对象的地址
}

int main()
{
    
    

    test01();

    system("pause");
    return 0;
}

Tengo entendido declarar una función global en la clase para que esta función pueda acceder a los miembros privados de la clase. El método de declaración es el siguiente.
(No consideres qué permisos son)

friend void goodGay(Building *building);

Además, en este ejemplo, se utiliza la transferencia de dirección (puntero) y se transfiere el puntero de la clase. Debe aprender este uso.

Compañera de clases

La clase es un amigo, por lo que la clase amigo puede acceder a las variables miembro privadas en la clase original. El código es el siguiente:

// arrayone.cpp -- small arrays of integers
#include <iostream>

using namespace std;

#include <string>
class Building;
class goodGay
{
    
    
public:
    goodGay();
    void visit();

private:
    Building *building;//定义了Building类的指针
};

class Building
{
    
    
    //告诉编译器 goodGay类是Building类的好朋友,可以访问到Building类中私有内容
    friend class goodGay;

public:
    Building();

public:
    string m_SittingRoom; //客厅
private:
    string m_BedRoom; //卧室
};

Building::Building()
{
    
    
    this->m_SittingRoom = "客厅";
    this->m_BedRoom = "卧室";
}

goodGay::goodGay()
{
    
    
    //这是一个初始化类的构造函数
    building = new Building;//building是goodgay类中的成员,这里对他进行了初始化,并且采用的是new指针方式
}

void goodGay::visit()
{
    
    
    cout << "好基友正在访问" << building->m_SittingRoom << endl;
    cout << "好基友正在访问" << building->m_BedRoom << endl;//访问了私有权限
}

void test01()
{
    
    
    goodGay gg;
    gg.visit();
}

int main()
{
    
    

    test01();

    system("pause");
    return 0;
}

Aquí usamos punteros como la definición de clase y usamos el operador new. No está claro por qué hicimos esto.
Lo importante es declarar en la clase Building:

friend class goodGay;

Por tanto, la clase Building contiene a la clase goodGay como amiga.

Función de miembro como amigo

Una función miembro es una función definida en una clase. Si queremos usar una función en una clase y usar la función para acceder a miembros privados en otra clase, podemos usar la función miembro como un amigo en la última clase. El código específico es como sigue:

// arrayone.cpp -- small arrays of integers
#include <iostream>

using namespace std;

#include <string>

class Building;

class GoodGay
{
    
    
public:
    GoodGay();
    void visit();  //让visit函数可以访问Building中私有成员
    void visit2(); //让visit2函数不可以访问Building中私有成员

    Building *building;
};

class Building
{
    
    
    //告诉编译器,GoodGay类下的visit成员函数作为本类的好朋友,可以访问私有成员
    friend void GoodGay::visit();

public:
    Building();

public:
    string m_LivingRoom; //客厅

private:
    string m_BedRoom; //卧室
};
//类外实现成员函数
Building::Building()
{
    
    
    m_LivingRoom = "客厅";
    m_BedRoom = "卧室";
}
GoodGay::GoodGay()
{
    
    
    building = new Building; //在堆区创建Building对象,并用指针building维护!!
}
void GoodGay::visit()
{
    
    
    cout << "visit 正在访问" << building->m_LivingRoom << endl;
    cout << "visit 正在访问" << building->m_BedRoom << endl;
}
void GoodGay::visit2()
{
    
    
    cout << "visit2 正在访问: " << building->m_LivingRoom << endl;
    //cout << "visit 正在访问" << building->m_BedRoom << endl;//不可以访问
}

void test01()
{
    
    
    GoodGay gg;
    gg.visit();
    gg.visit2();
}
int main()
{
    
    
    test01();
    system("pause");
    return 0;
}

Entre ellos, el más importante es la frase "declaración":

//告诉编译器,GoodGay类下的visit成员函数作为本类的好朋友,可以访问私有成员
friend void GoodGay::visit();

De esta manera, la función de visita en la clase GoodGay puede acceder a las variables de miembros privados en la clase Building.
Vale la pena mencionar que
se puede lograr el mismo efecto reemplazando esto con clase como amigo.
Así que pensemos que la función de miembro hacer amigos es una forma más refinada de declaración de amigos (puramente mi suposición).

Supongo que te gusta

Origin blog.csdn.net/qq_41883714/article/details/109478662
Recomendado
Clasificación