在c+中访问不同类中的类成员+; 我试图用C++来理解面向对象的编程。以下是一个最小的示例,其结果与我天真的期望不符: #include <iostream> class B { public: B (int val) : val(val) {;} int get_val() { return val; } int set_val(int a) { val = a; } private: int val; }; class A { public: A (B b) : b(b) {;} B get_b() { return b; } private: B b; }; int main(){ B b_main(5); std::cout << b_main.get_val() << std::endl; // Prints 5, which makes sense A a_main(b_main); std::cout << a_main.get_b().get_val() << std::endl; // Prints 5, which makes sense a_main.get_b().set_val(2); std::cout << a_main.get_b().get_val() << std::endl; // Why does this not print 2? return 0; }
现在我得到了想要的结果。相对于第一个代码段,代码应该是这样实现的吗?我想要一个与第一个代码片段相同的在c+中访问不同类中的类成员+; 我试图用C++来理解面向对象的编程。以下是一个最小的示例,其结果与我天真的期望不符: #include <iostream> class B { public: B (int val) : val(val) {;} int get_val() { return val; } int set_val(int a) { val = a; } private: int val; }; class A { public: A (B b) : b(b) {;} B get_b() { return b; } private: B b; }; int main(){ B b_main(5); std::cout << b_main.get_val() << std::endl; // Prints 5, which makes sense A a_main(b_main); std::cout << a_main.get_b().get_val() << std::endl; // Prints 5, which makes sense a_main.get_b().set_val(2); std::cout << a_main.get_b().get_val() << std::endl; // Why does this not print 2? return 0; },c++,oop,object,member,C++,Oop,Object,Member,现在我得到了想要的结果。相对于第一个代码段,代码应该是这样实现的吗?我想要一个与第一个代码片段相同的get_b()方法,但是如果这不是正确的方法,请告诉我。get_b返回私有变量b的副本,而不是实际变量。如果希望能够访问它,则需要返回对b的引用,以便可以操纵返回的值。您的get_b定义应如下所示: B& get_b() { return b; } 如果这是你想要做的。然而,这通常不是一个理想的解决方案。如果要主动更改b的值,应该编写一个set_b函数来操作变量。如果你真的经常使用这个变
get_b()
方法,但是如果这不是正确的方法,请告诉我。get_b返回私有变量b的副本,而不是实际变量。如果希望能够访问它,则需要返回对b的引用,以便可以操纵返回的值。您的get_b定义应如下所示:
B& get_b() { return b; }
如果这是你想要做的。然而,这通常不是一个理想的解决方案。如果要主动更改b的值,应该编写一个set_b函数来操作变量。如果你真的经常使用这个变量,读写它的值,你应该把它公开以便快速访问
在倒数第二行中,我将对象的值设置为2,那么为什么不打印2呢
因为您使用get\u B()
方法返回a\u main
中B
对象的副本。发生的情况是复制a_main
中的b
变量,即创建与b
成员相同的类b
的另一个对象,并将其返回给调用者。然后,修改新的B
对象。但是它与a_main
中的原始b
没有连接。这与可见性和成员访问权限关系不大
但是,在第二个示例中,您公开了a_main
中的b
成员,并直接对该对象进行操作,而不复制该对象,从而获得了成功的结果。public
修饰符更改的是,它允许您直接访问b
对象,从而产生效果
我找到了一些建议,尝试通过引用A
:A(B&B):B(B){;}
的构造函数来传递类型B的对象,但这也不起作用
那是行不通的。执行此操作时,将使用通过引用传递的值true初始化A::b
。但是引用只会导致没有额外的b
副本传递给正在制作的构造函数。此引用不会在传递给构造函数的b
和a::b
之间创建链接。可以说,它在另一端
顺便说一下,A(B&B):B(B){;}
认为c'tor参数名称与成员名称相同是一种不好的做法。将它们命名为类似的名称是一个好主意,但仍然可以添加下划线:a(B&\u B):B(\u B){;}
如果要在第一个代码段中获得相同的结果,请返回对b
的引用,如下所示:
B& get_b() { return b; }
但是,这是不可取的,因为您公开类a
的私有成员只是为了允许a
的客户端修改该成员的特定属性。最好在a
中提供一种方法来设置a::b
的val
属性,而不授予对a::b
的完全访问权
你肯定看到了:
也许是这样:
因为我有一种感觉,你来自Java,默认的是C++中的“通过引用”。
< P>只是为了完整性,你可以把这个问题作为C编程问题来解决,而不是使用C++编程中的所有java引用。当您从一个_main获取b_main时,返回的对象不会占用相同的内存地址#include <iostream>
class B {
public:
B (int val) : val(val) {;}
int get_val() { return val; }
int set_val(int a) { val = a; }
private:
int val;
};
class A {
public:
A (B b) : b(b) {;}
B get_b() { return b; }
private:
B b;
};
int main(){
B b_main(5);
B* addrb = &b_main;
std::cout << b_main.get_val() << std::endl; // Prints 5, which makes sense
std::cout<<"Address of b_main: "<<addrb<<std::endl;
A a_main(b_main);
B bt = a_main.get_b();
addrb = &(bt);
std::cout << a_main.get_b().get_val() << std::endl; // Prints 5, which makes sense
std::cout<<"Address of a_main.get_b(): "<<addrb<<std::endl;
a_main.get_b().set_val(2);
std::cout << a_main.get_b().get_val() << std::endl; // Why does this not print 2?
return 0;
}
#包括
B类{
公众:
B(int-val):val(val){;}
int get_val(){return val;}
int set_val(int a){val=a;}
私人:
int-val;
};
甲级{
公众:
A(B):B(B){;}
B get_B(){return B;}
私人:
B B;
};
int main(){
B B_干管(5);
B*addrb=&B_main;
标准::cout
#include <iostream>
class B {
public:
B (int val) : val(val) {;}
int get_val() { return val; }
int set_val(int a) { val = a; }
private:
int val;
};
class A {
public:
A (B b) : b(b) {;}
B get_b() { return b; }
private:
B b;
};
int main(){
B b_main(5);
B* addrb = &b_main;
std::cout << b_main.get_val() << std::endl; // Prints 5, which makes sense
std::cout<<"Address of b_main: "<<addrb<<std::endl;
A a_main(b_main);
B bt = a_main.get_b();
addrb = &(bt);
std::cout << a_main.get_b().get_val() << std::endl; // Prints 5, which makes sense
std::cout<<"Address of a_main.get_b(): "<<addrb<<std::endl;
a_main.get_b().set_val(2);
std::cout << a_main.get_b().get_val() << std::endl; // Why does this not print 2?
return 0;
}
#include <iostream>
class B {
public:
B (int val) : val(val) {;}
int get_val() { return val; }
int set_val(int a) { val = a; }
private:
int val;
};
class A {
public:
A (B b) : b(b) {;}
B* get_b() { return &b; }
private:
B b;
};
int main(){
B b_main(5);
//B* addrb = &b_main;
std::cout << b_main.get_val() << std::endl; // Prints 5, which makes sense
//std::cout<<"Address of b_main: "<<addrb<<std::endl;
A a_main(b_main);
//B bt = a_main.get_b();
//addrb = &(bt);
std::cout << a_main.get_b()->get_val() << std::endl; // Prints 5, which makes sense
//std::cout<<"Address of a_main.get_b(): "<<addrb<<std::endl;
a_main.get_b()->set_val(2);
std::cout << a_main.get_b()->get_val() << std::endl; // Why does this not print 2?
return 0;
}