0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

一部分だけをfriendな感じに

Posted at

何の話か

C++ 初心者です.
実際にそういうことをしたい場面があるわけではないんだけど,何故か以下のようなことをふと考えた.だけ.

class XY の friend にすると,X から Y の全てを触れる.
→ この「全て」ってのが嫌な場合にはどうする? っていう.

例えばこんな↓場合,どうすればいいかな? と.

class Y
{
	friend class X;
private:
	//コレはXに触らせたいが…
	void PrivateFunc1(){	std::cout << "PF1\n";	}
	//以下はXにも触らせたくない
	void PrivateFunc2(){	std::cout << "PF2\n";	}
	int m_Val = 77;
};

(1)Yを2分割

そんなことのために継承とか,何か嫌だな.

//Xがfirendな部分だけのclassを作って…
class IF_for_X
{
	friend class X;
protected:
	void PrivateFunc1(){	std::cout << "PF1\n";	}
};
//↑を継承する
class Y : public IF_for_X
{
private:
	void PrivateFunc2(){	std::cout << "PF2\n";	}
	int m_Val = 77;
};

(2)三店方式

直に friend にするのではなく,XY の間に1つそれ用のを噛ませる.

class Y
{
public:
	class IF_for_X
	{
		friend class X;
		static void PrivateFunc1( Y &y ){	y.PrivateFunc1();	}
	};
	
private:
	void PrivateFunc1(){	std::cout << "PF1\n";	}
	void PrivateFunc2(){	std::cout << "PF2\n";	}
	int m_Val = 77;
};

class X
{
public:
	void Test( Y &y ){	Y::IF_for_X::PrivateFunc1( y );	}
};

(3)Xにしか作れないものを要求

public だけども実質 X からしか使えないでしょ,っていう.

class Permit
{//Xにしか作れない
	friend class X;
	Permit(){}
};

class Y
{
public:
	//Xにしか作れないものを引数にした public なメンバ関数を用意する
	void PF1( const Permit & ){	PrivateFunc1();	}
private:
	void PrivateFunc1(){	std::cout << "PF1\n";	}
	void PrivateFunc2(){	std::cout << "PF2\n";	}
	int m_Val = 77;
};

class X
{
public:
	void Test( Y &y ){	y.PF1( Permit{} );	}
	void Test2( Y &y ){	y.PF1( {} );	}	//{}とだけ書くのでもいける模様
};

……とかいうのを実験してたところ,↑の Permit のコンストラクタを

Permit() = default;

って書いたら,

int main()
{
	Permit p;	//エラー:アクセスできません
	Permit *p = new Permit();	//エラー:アクセスできません
	Permit p{};	// Permit の ctor を =default とすると通ってしまう?
}

という結果になって困惑中.Why?

0
0
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?