简体   繁体   English

C++:成员不可访问 - 使用朋友 function 允许一个 class 修改另一个 ZA2F2ED4F8EBC2CBB4ZC2A 成员数据

[英]C++: Member is inaccessible - using friend function to allow one class to modify another class member data

Okay, I have looked all over for an answer to this.好的,我已经到处寻找答案了。

I am trying to set up a system where an object's private members can be modified only through two member functions of a separate class.我正在尝试建立一个系统,其中只能通过单独的 class 的两个成员函数来修改对象的私有成员。

Here is the header content of the object to be modified, table.h:这里是要修改的object的header内容,table.h:

#ifndef TABLE_H
#define TABLE_H

#include "party.h"

/*
Seats a party for their dining experience at the restaurant.
*/
class table
{
    friend void server::seatGuests(const table &, const party &);
    friend void server::cleanTable(const table &);

private:
    const unsigned int cap_; //guest capacity (shouldn't change)
    const unsigned int id_;  //table id (shouldn't change)
    mutable bool isTaken_;   //flag (changeable by friend functions)
    party *const group_;     //party seated at the table (starts off as null)

public:
    table::table(const unsigned int id, const unsigned int cap = 4); //ctor
    inline const unsigned int table::getCap() const { return cap_; }
    inline const unsigned int table::getId() const { return id_; }
    inline const bool table::isTaken() const { return isTaken_; }
    inline const party *const table::getParty() const { return group_; };
};

void server::seatGuests(const table &t, const party &p)
{
    t.isTaken_ = false;
}

#endif // TABLE_H

here is server.h:这是server.h:

class server : public employee
{
private:
public:
    explicit server::server();
    void server::seatGuests(const table &, const party &);
    void server::cleanTable(const table &);
};

...

I am getting the following error: member "table::isTaken_" (declared at line 17) is inaccessible我收到以下错误: member "table::isTaken_" (declared at line 17) is inaccessible

The server.h file is included in table.h indirectly, as party.h includes restaurant.h which includes server.h. server.h 文件间接包含在 table.h 中,因为 party.h 包含 restaurant.h,其中包含 server.h。

I tried putting this in table.h before:我之前试过把它放在 table.h 中:

class server;
namespace server {
   void server::seatGuests(const table &, const party &);
   void server::cleanTable(const table &);
}

But this just gave me more headaches, as the compiler would spit out something like, "class server has no member 'seatGuests' or 'cleanTable'", which I figured was due to some inclusion conflict.但这只是让我更头疼,因为编译器会吐出类似“类服务器没有成员'seatGuests'或'cleanTable'”之类的东西,我认为这是由于一些包含冲突。 This conflict is why I've declared the function in the original server.h file and not in the table.h file.这个冲突是我在原始 server.h 文件而不是 table.h 文件中声明 function 的原因。

That being said, sources I've read such as this one state that the implementation of the friend function should be in the class whose data is being modified, which is what I've done.话虽如此,我读过的消息来源,例如state ,朋友 function 的实现应该在 class 中,其数据正在被修改,这就是我所做的。

All that aside, the compiler still thinks the member data is not accessible.除此之外,编译器仍然认为成员数据不可访问。 Can anyone see what I'm doing wrong here?谁能看到我在这里做错了什么?

Let me know if you want me to post more code.如果您希望我发布更多代码,请告诉我。

Thanks in advance.提前致谢。

EDIT编辑

Apologies for the delay in posting the compiler output.对于延迟发布编译器 output 表示歉意。 Please see below:请看下面:

> Executing task: clang++ -Wall -std=c++17 -stdlib=libc++ -o main.out /Users/ajm/Projects/restaurant/cpp/main/main.cpp -I/Users/ajm/Projects/restaurant/cpp/main/ -I/Users/ajm/Projects/restaurant/cpp/restaurant/ -I/Users/ajm/Projects/restaurant/cpp/people/ -I/Users/ajm/Projects/restaurant/cpp/people/workers/ -I/Users/ajm/Projects/restaurant/cpp/data/ --debug <

In file included from /Users/ajm/Projects/restaurant/cpp/main/main.cpp:1:
In file included from /Users/ajm/Projects/restaurant/cpp/main/simulation.h:4:
In file included from /Users/ajm/Projects/restaurant/cpp/restaurant/restaurant.h:4:
In file included from /Users/ajm/Projects/restaurant/cpp/restaurant/tablespace.h:4:
In file included from /Users/ajm/Projects/restaurant/cpp/restaurant/table.h:4:
In file included from /Users/ajm/Projects/restaurant/cpp/people/workers/server.h:4:
In file included from /Users/ajm/Projects/restaurant/cpp/people/workers/employee.h:5:
In file included from /Users/ajm/Projects/restaurant/cpp/main/../data/job.h:4:
/Users/ajm/Projects/restaurant/cpp/people/party.h:25:16: error: unknown type name 'restaurant'
    void start(restaurant &spot);
               ^
In file included from /Users/ajm/Projects/restaurant/cpp/main/main.cpp:1:
In file included from /Users/ajm/Projects/restaurant/cpp/main/simulation.h:4:
In file included from /Users/ajm/Projects/restaurant/cpp/restaurant/restaurant.h:4:
In file included from /Users/ajm/Projects/restaurant/cpp/restaurant/tablespace.h:4:
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:8:11: error: redefinition of 'server' as different kind of
      symbol
namespace server
          ^
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:7:7: note: previous definition is here
class server;
      ^
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:10:23: error: unknown type name 'table'
void seatGuests(const table &t, const party *const p);
                      ^
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:11:23: error: unknown type name 'table'
void cleanTable(const table &t);
                      ^
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:13:31: error: unknown type name 'table'
void server::seatGuests(const table &t, const party *const p)
                              ^
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:18:31: error: unknown type name 'table'
void server::cleanTable(const table &t)
                              ^
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:42:25: error: out-of-line declaration of 'seatGuests' does not
      match any declaration in 'server'
    friend void server::seatGuests(const table &t, const party *const p);
                        ^~~~~~~~~~
/Users/ajm/Projects/restaurant/cpp/restaurant/table.h:43:25: error: out-of-line declaration of 'cleanTable' does not
      match any declaration in 'server'
    friend void server::cleanTable(const table &t);
                        ^~~~~~~~~~
8 errors generated.
The terminal process terminated with exit code: 1

The declaration of server::seatGuests and server::cleanTable must appear before the friend declaration in table . server::seatGuestsserver::cleanTable的声明必须出现在table中的friend声明之前。 #include "server.h" appears before the declaration of table so that should be enough right? #include "server.h"出现在table的声明之前,这样就足够了,对吧? Well, server includes table and table includes server so we have cyclic dependencies.好吧, server包括tabletable包括server ,所以我们有循环依赖。 To get around this, table should include server and server should forward declare table .为了解决这个问题, table应该包括server并且server应该转发 declare table

// table.h

#include "party.h"

class table
{
    friend void server::seatGuests(const table &, const party &);
    friend void server::cleanTable(const table &);
};



// server.h

class table;
class party;

class server : public employee
{
public:
    explicit server();
    void seatGuests(const table &, const party &);
    void cleanTable(const table &);
};

Cyclic dependencies and friend declarations seem like bad design to me.循环依赖和友元声明对我来说似乎是糟糕的设计。 Instead of using a forward declaration to get around this, you might want to rethink the design.您可能需要重新考虑设计,而不是使用前向声明来解决这个问题。 Find a way to avoid the cycle and avoid the friend declarations.找到一种避免循环并避免友元声明的方法。 My answer is a workaround, not a solution.我的回答是解决方法,而不是解决方案。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM