《深入理解C++11》的扩展的friend语法例子让人抓狂

CodingLife99 2018-05-30 04:39:52
目前在总结现代C++的新特性,看了《深入理解C++11》这本书。
今天看到扩展的friend语法这一节,遇到了问题。本节电子版内容参见:https://book.2cto.com/201306/25354.html

未改良前的代码如代码清单2-21所示(在Linux下按照下面的编译指令能够通过),接着作者总结出了这种方法4点不好,给出了改良版代码(如代码清单2-22所示)。我要吐槽的是,反复试了好久,这改良版根本就不能够通过编译,感觉代码写的相当的鬼畜。(不明白之处在代码清单2-22的39,41,56行处)

希望各路大神能够鼎力相助。谢过。



代码清单2-21

#include<iostream>
using namespace std;

// 为了方便测试,进行了危险的定义
#ifdef UNIT_TEST
#define private public
#endif
class Defender {
public:
void Defence(int x, int y){}
void Tackle(int x, int y){}

private:
int pos_x = 15;
int pos_y = 0;
int speed = 2;
int stamina = 120;
};

class Attacker {
public:
void Move(int x, int y){}
void SpeedUp(float ratio){}

private:
int pos_x = 0;
int pos_y = -30;
int speed = 3;
int stamina = 100;
};

#ifdef UNIT_TEST
class Validator {
public:
void Validate(int x, int y, Defender & d){}
void Validate(int x, int y, Attacker & a){}
};

int main() {
Defender d;
Attacker a;
a.Move(15, 30);
d.Defence(15, 30);
a.SpeedUp(1.5f);
d.Defence(15, 30);
Validator v;
v.Validate(7, 0, d);
v.Validate(1, -10, a);
return 0;
}
#endif
// 编译选项:g++ 2-9-3.cpp -std=c++11 -DUNIT_TEST





代码清单2-22

#include<iostream>
using namespace std;

template <typename T> class DefenderT {
public:
friend T;
void Defence(int x, int y){}
void Tackle(int x, int y){}

private:
int pos_x = 15;
int pos_y = 0;
int speed = 2;
int stamina = 120;
};

template <typename T> class AttackerT {
public:
friend T;
void Move(int x, int y){}
void SpeedUp(float ratio){}

private:
int pos_x = 0;
int pos_y = -30;
int speed = 3;
int stamina = 100;
};

using Defender = DefenderT<int>; // 普通的类定义,使用int做参数
using Attacker = AttackerT<int>;

#ifdef UNIT_TEST
class Validator {
public:
void Validate(int x, int y, DefenderTest & d){}
// 该行和下一行均报错:语法错误
void Validate(int x, int y, AttackerTest & a){}
//我在想这里的AttackerTest 是下面两行定义的,尝试把下面的两行提到前面错误变得更多了
};

using DefenderTest = DefenderT<Validator>; // 测试专用的定义,Validator类成为友元
using AttackerTest = AttackerT<Validator>;

int main() {
DefenderTest d;
AttackerTest a;
a.Move(15, 30);
d.Defence(15, 30);
a.SpeedUp(1.5f);
d.Defence(15, 30);
Validator v;
v.Validate(7, 0, d) ;
//此处和下一行均报错:函数不接受3个参数
v.Validate(1, -10, a);
return 0;
}
#endif
// 编译选项:g++ 2-9-4.cpp -std=c++11 -DUNIT_TEST
...全文
673 3 打赏 收藏 转发到动态 举报
写回复
用AI写文章
3 条回复
切换为时间正序
请发表友善的回复…
发表回复
CodingLife99 2018-05-31
  • 打赏
  • 举报
回复
引用 2 楼 hdt 的回复:
using DefenderTest = DefenderT<Validator>; // 测试专用的定义,Validator类成为友元 using AttackerTest = AttackerT<Validator>; 把这两行提到 class Validator 之前,因为他的成员函数用到了这些定义 又因为 using DefenderTest = DefenderT<Validator>; 用到了 Valkidator 所以 要在这句话之前,前置声明一下 class Validator;
感谢你能够耐心阅读我的问题,我试了下你说的方法有效,谢谢啦 !
真相重于对错 2018-05-31
  • 打赏
  • 举报
回复
using DefenderTest = DefenderT<Validator>; // 测试专用的定义,Validator类成为友元 using AttackerTest = AttackerT<Validator>; 把这两行提到 class Validator 之前,因为他的成员函数用到了这些定义 又因为 using DefenderTest = DefenderT<Validator>; 用到了 Valkidator 所以 要在这句话之前,前置声明一下 class Validator;
赵4老师 2018-05-30
  • 打赏
  • 举报
回复
做个可能不太恰当的比喻: 人想让狗帮忙逮只兔子,可是人说话狗听不懂,于是人发明了一种介乎人言和狗语之间的语言,即口令。 人想让电脑帮忙做计算,可是人话电脑听不懂,于是人发明了一种介乎人言和汇编机器码之间的语言,即C语言。 人对狗的口令得让人容易学、也得让狗容易懂。 C语言同样得让人容易学、也得让电脑容易懂。 相比之下C++、Java就是人学得费劲、电脑也经常闹不懂。
内容概要:本文系统研究了在强弱电网适配场景下,构网型(GFM)与跟网型(GFL)逆变器并联系统的协同控制逻辑及其暂态动态行为,重点依托Simulink仿真平台构建混合并网系统模型,深入分析两类逆变器在不同电网强度条件下的交互特性、频率响应机制、稳定性表现及抗扰能力。研究涵盖分层控制架构设计、异构控制策略对比、频率扰动响应规律以及多工况暂态性能评估,探讨了GFM与GFL逆变器在功率支撑、电压频率调节和系统稳定性方面的互补性与协同机制,旨在提升高比例新能源接入背景下并网系统的适应性、鲁棒性与动态性能。; 适合人群:具备电力电子、新能源并网、自动控制或电力系统仿真等相关专业知识背景,从事新型电力系统控制、微电网运行、逆变器控制策略研究的研究生、科研人员及工程技术人员。; 使用场景及目标:①深入理解构网型与跟网型逆变器在强弱电网中的协同工作机理与动态交互特性;②掌握异构逆变器并联系统的建模方法、协同控制策略设计与暂态仿真分析流程;③为高渗透率新能源系统的稳定性分析、控制优化及工程应用提供理论依据和技术参考。; 阅读建议:建议结合Simulink仿真实例进行动手实践,重点关注控制策略的实现细节、参数整定方法及多工况仿真结果的动态响应分析,同时可参考文中提及的相关博士论文复现案例以深化对理论机制的理解。

65,213

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧