好友和静态成员函数具有什么样的成员访问权限
What kind of member access do friend and static member functions have?
我想知道friend
函数和static
成员函数对类对象有什么样的类成员访问。具体来说,区别是什么以及为什么要使用其中一个而不是另一个。我的理解是,声明为类的friend
或static
成员的函数都可以访问该类任何实例的私有成员。
我将举一个简单的例子来说明为什么它们看起来和我如此相似。函数operator<
和MyClass::lessThan
似乎都有相同的访问权限,并且可以做完全相同的事情。
class MyClass {
friend bool operator<(const MyClass &left, const MyClass &right);
public:
MyClass(int pub, int priv) : m_pub(pub), m_priv(priv) {}
static bool lessThan(const MyClass &left, const MyClass &right);
int m_pub;
private:
int m_priv;
};
bool operator<(const MyClass &left, const MyClass &right) {
return ( (left.m_pub < right.m_pub) && (left.m_priv < right.m_priv) );
}
bool MyClass::lessThan(const MyClass &left, const MyClass &right) {
return ( (left.m_pub < right.m_pub) && (left.m_priv < right.m_priv) );
}
int main(int argc, const char* argv[]) {
MyClass a(1, 2),
b(3, 4),
c(-1, 1);
cout << "a < b = " << (a<b) << endl;
cout << "a lessThan b = " << MyClass::lessThan(a,b) << endl;
cout << "a < c = " << (a<c) << endl;
cout << "a lessThan c = " << MyClass::lessThan(a,c) << endl;
}
显然,这是一个简化的例子,但我想我的问题分为两部分:
- 在成员访问方面,朋友函数和静态函数之间有什么区别
- 在决定使用哪一种时,应该考虑哪些因素
请记住,尽管friend函数的原型出现在类定义中,但friendriend函数是在类之外定义的,但friendriend函数用于生成测试程序类。
当对象类应该只共享变量的一个副本时,将使用静态数据成员。因此,当所有类成员只需要一个副本就足够时,必须使用静态数据成员来保存存储。
对于静态成员函数,您可以查看以下内容:何时使用静态成员函数?
- 他们都可以接触到班上的所有成员,包括私人成员
- 您需要决定一个函数在逻辑上是否属于它需要访问其成员的类,或者它是否属于另一个类,或者根本不属于任何类。在第一种情况下(逻辑上属于类的函数),使函数为静态的;在第二种情况下,让它成为一个朋友,并根据您的设计添加到它逻辑上所属的类或命名空间中
它们是不同的概念:
如果一个类、方法或函数是类X的朋友,则该类、函数或方法可以访问被声明为私有的类X的成员,因此通常不能在类之外访问
class A{
private:
int x;
friend void foo(A& a);
};
void foo(A& a){
a.x = 3; //Access okay, foo is a friend of A
}
void bar(A& a){
a.x = -1; // Compiler will complain A::x is private
}
静态成员是在该类的所有对象实例之间共享的数据成员,或者是可以在没有该类的实例对象的情况下调用的方法。
class B{
private:
static int y;
public:
static void printY();
void alterY();
}
int B::y=3;
void B::printY(){
cout<<y;
}
void B::alterY(){
y++;
cout<<y;
}
B b1,b2;
B::printY();// will output 3
b1.alterY();// will output 4
b2.alterY();// will output 5
静态方法可以在不经过类实例的情况下调用,因此它们没有任何直接访问权限,它们类似于全局函数,但嵌套在类的命名空间中。但是,如果您给它们一个该类的实例作为参数,它们将能够访问成员变量,而无需像非静态方法一样通过访问器。与静态方法一样,友元函数如果您将其友元类的实例作为参数提供给它们,它们将能够直接访问成员变量。
在成员访问方面,朋友函数和静态函数之间有什么区别?
无。他们都有完全的访问权。
在决定使用哪一种时,应该考虑哪些因素?
它完全取决于上下文以及什么使代码更容易阅读。
在你上面的例子中,我肯定更喜欢bool operator<()
而不是MyClass::lessThan()
,因为它使代码阅读起来更直观。
- 这是关于成员访问规则的正确摘要吗
- 为什么我在空指针错误(链表)中获取成员访问权限
- 成员访问是否在空指针上定义C++?
- C++ IDE 不会推断/自动完成对模板类中的 std::array 下标表达式的成员访问
- 为什么类成员数据必须是静态的才能被模板化类的模板化结构成员访问
- 为什么c++允许成员函数定义中实例的私有成员访问
- C/C++ 包含点的宏参数(成员访问运算符)
- 访问说明符(私有/公共/受保护)如何在内部工作(限制成员访问)?
- 如何将超类的受保护成员访问到其派生类. 如果已在派生类中声明了具有相同名称的函数?
- 内部类私有成员访问和封闭的友好性
- 通过 C++ 中的另一个结构成员访问结构
- 具体化 PRVALUES 成员访问的 decltype 行为不正确
- 常量表达式中的静态成员访问
- XVALUE来自类成员访问表达式
- 未经授权的私有类成员访问会产生编译时错误而不是运行时错误?
- 在 c++ 中,为什么 -> 被称为二进制中缀指针成员访问运算符?
- 如何访问模板参数的成员?“成员访问不完整的类型”
- 不明确的可变参数类成员访问
- C 受保护的成员访问
- 将typeID转换为静态成员访问(C )的命名空间