C_and_CPP 板


LINE

class如何设计,这个题目太大了 没办法只用一篇文章交待完毕,下面只能提我想到的 (1)class vs struct vs union union用途比较特殊,不再特别提 traits、metafunction、functor,使用struct 有不变式者使用class,否则用struct 补充: 这里说明一下如何判断有无不变式 当data成员可以各自任意独立变更内容时,表示没有不变式 例如一个类别有月、日栏位,哪些日合法要看月的值,有不变式 或是有一栏位表示元素数量,一栏位指向各元素存放位置,也有不变式 (2)3/5/0法则 除非必要,否则不要自己写copy、move、dtor 如果写了其中一个,通常也要写其他四个成员函数 (3)obj成员 vs ptr成员 vs ref成员 先判断采组合还是聚合,再判断是否有降低类型相依性的需要 smart ptr,有所有权 raw ptr,尽量让其没有所有权(见补充) ref,没有所有权,而且不能改变值 尽量用std::function取代函数指标 补充: C++ Core Guidelines R.3与R.4,建议让raw ptr与ref没有所有权 但raw ptr有例外,例如旧代码,或是底层实作的需要 (4)static成员 vs non-static成员 成员基於类别,static成员 成员基於物件,non-static成员 (5)public权限 vs private权限 vs protected权限 data成员: 各成员之间有不变式关系,private权限 各成员之间无不变式关系,public权限 避免protected data non-const data权限要一样 成员函数: 提供给任意使用者的介面,public权限 仅提供给子类的介面,protected权限 只提供类别内部使用,private权限 (6)public继承 vs private继承 vs protected继承 有"IS-A"或"-ABLE"关系,继承介面(可能还有实作),public继承 有"HAS-A"关系,仅继承实作,private继承 补充: http://www.gotw.ca/publications/mill06.htm private继承跟protected继承可以用在受控制的多型 这用途很罕见,所以protected继承基本上可以忽略 (7)private继承 vs 组合 在"HAS-A"关系的前提下考虑这个 优先用组合,除非以下情况(细节见Effective C++ Item 39) 为了节省empty class占用的空间 需要用到protected成员 需要改写父类的virtual函数,例如template pattern (8)public继承 vs 组合 https://isocpp.org/wiki/faq/multiple-inheritance 看上面连结的经验法则1 主要目的是代码重用时,组合 主要目的是多型时,继承 补充: 记住,继承的耦合度高於组合 继承的主要目的不是代码重用,尽量避免实作继承 (9)virtual函数 vs non-virtual函数 让子类只继承介面,pure virtual函数 让子类继承介面跟预设实作,impure virtual函数 提供预设实作并强迫子类显式呼叫,为pure virtual函数提供定义 让子类继承介面跟强制实作,non-virtual函数 让子类只改写方法的某些步骤,用NVI包装virtual函数(template pattern) 多型类别必须有virtual dtor 补充: 记得预设参数是静态绑定,不要试图改写 (10)operator overloading 除非必要,否则不要重写 尽量避免重写operator&&跟operator||,会失去短路求值特性 尽量避免重写unary &,遇到incomplete type会导致结果无法预期 operator+以operator+=来实作,以此类推 operator+设计成非成员函数,operator+=设计成成员函数,以此类推 unary设计成成员函数,binary设计成非成员函数 postfix ++以prefix ++实作,以此类推 operator=不要设virtual 如果重写类型转换函数,请宣告成explicit,除非希望隐式转换 (11)ctor 不要自己写一个只初始data成员的default ctor 单参数ctor(不含copy跟move)宣告成explicit,除非希望隐式转换 初始过程如果想要有虚函数的行为,请改用factory pattern 考虑是否需要用using继承父类的ctor (12)多型类别禁止public copy/move 如果想复制,请改用prototype pattern (13)exception safety dtor、swap、move、回收函数必须做到nothrow default ctor、operator==(含其他比较运算子)尽量做到nothrow (14)当函数需要直接存取内部成员时才作为成员函数 以下为例外情况: 虚函数 operator overloading另有一套判断方式 重载集合不是每个函数都会直接存取内部成员 返回this的函数 (15)如果有作为成员函数的需要,再继续判断是否改用friend函数 https://isocpp.org/wiki/faq/friends 第一个函数参数不是该物件本身(见补充),friend函数 涉及binary运算,friend函数 其余情况,优先用成员函数 补充: 应该是在讲std::invoke (16)friend函数 vs static成员函数 vs non-static成员函数 如果经过(14)跟(15)仍无法决定,可以继续参考下面 如果无法用ADL找到该函数的声明,不考虑friend函数 如果需要相当於this的参数,不考虑static成员函数 如果不要相当於this的参数,不考虑non-static成员函数 补充: http://www.gotw.ca/publications/mill02.htm 非成员函数如果不满足介面原则,就没有设计成friend的意义 static成员函数如果需要this,就没有不用non-static版本的理由 (17)const成员函数 vs non-const成员函数 除非确实需要修改data成员,否则选择const成员函数 (18)动态多型 vs 静态多型 优先使用动态多型,除非有用CRTP消除virtual函数开销的必要 (19)函数的定义是否放在class body 为了降低编译相依性或不要inline,不放 为了可读性或inline,放 补充: virtual函数不会inline,ctor跟dtor尽量不要inline 除非必要,否则不考虑函数是否inline 函数定义如果不放在class body,则定义应放在cpp档 (20)多重继承 https://isocpp.org/wiki/faq/multiple-inheritance 考虑bridge pattern跟nested generalization能否作为替代方案 补充: 使用多重继承需要很多前置知识,谨慎使用 (21)虚拟继承 虚拟继承的主要用途是搭配多重继承 尽量避免在virtual base放data (22)如果需要限制继承深度 优先考虑final 限制之後往下最多可以继承几层,虚拟继承 + private ctor (23)design pattern 视使用情境而定,例如 strategy,动态切换演算法 adapter,解决介面不相容的问题 singleton,确保一个类只有一个实例 (24)mixin 主要目的是代码重用,由任意个元件组成一个新类别,有下面两种方式实现 可变模板 + 多重继承,每个基类皆为一个元件 模板 + 单继承,每层皆为一个元件 补充: 每个元件功能尽可能单一化,且采public继承 public继承一般不是为了代码重用,所以使用mixin前请先了解一般的继承用法 多重继承版本,mixin元件可以共享方法,但要转型才能使用 单继承版本,mixin元件只能单向共享内层的方法,不用转型就能使用 (25)常数 执行期常数,const 编译期常数 + 有使用具名enum的必要,enum class 编译期常数 + 一般情况,constexpr 补充: enum每个常数之间要有足够的关联,不能只用来包装一堆无关常数 用enum class取代enum,可以防止隐式转型及名称污染 (26)类型成员 nested class:不要同时定义class及声明该类型的变数 enum:不要同时定义enum及声明该类型的变数 类型别名:用using取代typedef,因为前者可读性高又能用在alias template 补充: data成员、成员函数、类型成员应按性质各自集中摆放 故类型成员不宜跟data成员混在一起 --



※ 发信站: 批踢踢实业坊(ptt.cc), 来自: 36.237.69.224 (台湾)
※ 文章网址: https://webptt.com/cn.aspx?n=bbs/C_and_CPP/M.1624780030.A.7B4.html
1F:推 beatssola: 推06/28 01:20
2F:→ loveflames: 再增加一项,因为static成员函数有办法间接存取non-st06/28 18:45
3F:→ loveflames: atic成员06/28 18:45
※ 编辑: loveflames (36.237.69.224 台湾), 06/28/2021 18:48:25
4F:推 FY4: 推 06/28 23:50
5F:→ KanzakiHAria: singleton最简单的方式把解构建构private 06/29 01:13
6F:→ KanzakiHAria: 加个return static local自己的get instance函数 06/29 01:14
7F:→ loveflames: 话说policy based design我找不到不改成组合的理由 06/29 10:02
8F:→ loveflames: 而组合没办法取代mixin的横向展延性质 06/29 10:04
9F:推 unmolk: 感谢分享!获益良多 07/02 17:26
10F:推 shibin: 推 07/02 19:09
※ 编辑: loveflames (125.227.113.163 台湾), 07/06/2021 12:10:58
11F:→ loveflames: 後来补上几个新项目 07/06 12:11
12F:推 hhashoww: 新手看不懂 但还是推! 感谢整理 07/24 18:41
13F:→ loveflames: 语法看到一定程度应该就看得懂了,这篇主要是提供选 07/25 00:21
14F:→ loveflames: 择的方式 07/25 00:21







like.gif 您可能会有兴趣的文章
icon.png[问题/行为] 猫晚上进房间会不会有憋尿问题
icon.pngRe: [闲聊] 选了错误的女孩成为魔法少女 XDDDDDDDDDD
icon.png[正妹] 瑞典 一张
icon.png[心得] EMS高领长版毛衣.墨小楼MC1002
icon.png[分享] 丹龙隔热纸GE55+33+22
icon.png[问题] 清洗洗衣机
icon.png[寻物] 窗台下的空间
icon.png[闲聊] 双极の女神1 木魔爵
icon.png[售车] 新竹 1997 march 1297cc 白色 四门
icon.png[讨论] 能从照片感受到摄影者心情吗
icon.png[狂贺] 贺贺贺贺 贺!岛村卯月!总选举NO.1
icon.png[难过] 羡慕白皮肤的女生
icon.png阅读文章
icon.png[黑特]
icon.png[问题] SBK S1安装於安全帽位置
icon.png[分享] 旧woo100绝版开箱!!
icon.pngRe: [无言] 关於小包卫生纸
icon.png[开箱] E5-2683V3 RX480Strix 快睿C1 简单测试
icon.png[心得] 苍の海贼龙 地狱 执行者16PT
icon.png[售车] 1999年Virage iO 1.8EXi
icon.png[心得] 挑战33 LV10 狮子座pt solo
icon.png[闲聊] 手把手教你不被桶之新手主购教学
icon.png[分享] Civic Type R 量产版官方照无预警流出
icon.png[售车] Golf 4 2.0 银色 自排
icon.png[出售] Graco提篮汽座(有底座)2000元诚可议
icon.png[问题] 请问补牙材质掉了还能再补吗?(台中半年内
icon.png[问题] 44th 单曲 生写竟然都给重复的啊啊!
icon.png[心得] 华南红卡/icash 核卡
icon.png[问题] 拔牙矫正这样正常吗
icon.png[赠送] 老莫高业 初业 102年版
icon.png[情报] 三大行动支付 本季掀战火
icon.png[宝宝] 博客来Amos水蜡笔5/1特价五折
icon.pngRe: [心得] 新鲜人一些面试分享
icon.png[心得] 苍の海贼龙 地狱 麒麟25PT
icon.pngRe: [闲聊] (君の名は。雷慎入) 君名二创漫画翻译
icon.pngRe: [闲聊] OGN中场影片:失踪人口局 (英文字幕)
icon.png[问题] 台湾大哥大4G讯号差
icon.png[出售] [全国]全新千寻侘草LED灯, 水草

请输入看板名称,例如:e-shopping站内搜寻

TOP