良好的程序设计/避免多重冗余检查的最佳实践(例如在C++中)
Good program design/best practice to avoid multiple redundant checks (eg. in C++)
假设我有一些函数(例如method1()
和method2()
),并且只有在满足某些条件的情况下才能执行这些函数中的每一个(对于这个简单的例子,将其称为对布尔值的检查)。为了隔离条件检查,我将检查放在每个函数中,例如
void method1()
{
if (bDoSomething) {
doSomething1();
doSomething2();
}
}
void method2()
{
if (bDoSomething) {
doSomething1();
doSomething3();
}
}
然而,doSomethingN()
函数也可以在method1()
和method2()
之外单独调用,因此我将条件检查添加到每个doSomethingN()
函数中,例如
void doSomething1() {
if (bDoSomething) {
doWork1();
}
}
此外,假设method1()
和method2()
可以从同一个函数中调用,例如
void func1() {
method1();
method2();
}
这导致在调用func1()
、method1()
或method2()
时对同一条件进行多次检查。有什么更好的方法可以避免多重检查?
关于如何最好地设计/构建程序以尽量减少这种事情,有什么好的资源吗?
取决于问题的具体细节。。您可以做的一件事是将检查放在doSomething
函数中。
void doSomething1() {
if(!bDoSomething) return;
....
}
您不需要检查外部函数中的条件,只需调用适当的函数,它们就会在需要时执行。您仍然可以出于自我记录的目的保留它。
也有可能您的代码比需要的复杂得多。要进行诊断,您需要更多的细节和大局。
p.s您可以尝试我的检查风格,即如果为负数则返回,而不是如果为正数则处理,这有时可能会使代码更干净,但会降低缩进级别。
假设您有两个类:Private
和Captain
。让我们以Captain
s命令Private
s的方式使用它们。Captain
s想要什么,Private
s做什么
void Captain::HaveSomethingDone() {
if(AmIAtAnAdvantage()) {
for(Private& p : m_privates) {
p.Attack();
}
}
else if(IsSituationStalemate()) {
for(Private& p : m_privates) {
p.Hold();
}
}
else if(IsALosingBattle()) {
for(Private& p : m_privates) {
p.Retreat();
}
}
}
在上面的例子中,Private
无条件地做Captain
想要的事情,因为Captain
知道它在做什么。通过这种方式,我们可以清楚地分离关注点。
另一个,现在是方法。举个例子:
void DoSomething() {
if(ShouldPrint()) {
Print();
}
if(ShouldCleanUp()) {
CleanUp();
}
// ...
}
在上面的例子中,DoSomething()
知道它应该做什么。它是决定它应该做做什么的人。因此,Print()
和CleanUp()
方法应该无条件地做它应该做的事情。Print()
打印。CleanUp()
清理。
现在想想。
我认为避免多重条件检查的最佳方法是在代码中实现State设计模式。这种设计模式只允许您将代码用作状态机,这意味着根据对象状态的状态,您可以调用所需的方法。你可以在这里获得更多信息http://en.wikipedia.org/wiki/State_pattern
好吧,我想你的检查很重,否则我不会担心双重调用,因为你的代码会更干净。
我心里有两件事:
-
将第一个检查结果缓存在类中的某个位置。
-
生成调用者对象,只有当您的条件为true时才能创建该对象。
类似的东西:
class ConditionalCaller
{
public:
void Method1();
void Method2();
};
class YourClass
{
public:
ConditionalCaller* GetCaller()
{
if (CanGetCaller())
return new ConditionalCaller();
return NULL;
}
bool CanGetCaller();
};
有几种不同的情况:
method1
和method2
是私有的,您可以控制它们在哪里被调用,并且您可以保证检查所有预条件。在这种情况下,您可以在这些方法中避免这些测试method1
和method2
是公共的,您记录了必须满足几个条件(如std中的容器)作为先决条件method1
和method2
检查它们的前提条件并相应地响应(抛出和异常,什么都不做…)- 您可以创建方法的已检查和未检查版本(混合其他变体),并通过不同的名称
*_checked
或其他参数(如notthrow-new)来区分它们
但请记住Scott Meyers:使界面易于正确使用,难以错误使用。
因此,您必须做出决定并将其记录下来。
- 在C#中处理C++指针而不使用unsafe的最佳方法
- 在C++中,将大的无符号浮点数四舍五入为整数的最佳方法是什么
- 实现无开销push_back的最佳方法是什么
- 在c代码之间共享数据的最佳方式
- 使用std::source_location报告错误的最佳实践
- 派生类销毁的最佳实践是什么
- 将寄存器设计成可由C和C++访问的外设的最佳实践
- 在两台机器之间进行时间戳的最佳c++chrono函数是什么
- 使用QQuickFramebufferObject时同步数据的最佳方式是什么
- 在C++中向零方向近似的最佳方法
- 使用不同的CRT将新的C++代码与旧的(二进制)组件隔离开来的最佳方法是什么
- 从嵌套在std::映射中的std::列表中删除元素的最佳方式
- 如果条件为TRUE(最佳方式?),则在do while循环中后置增量
- 检测win32服务创建和删除的最佳方法
- 在reactor中存储eventHandlers的最佳方式是什么
- 在C++中样板"冷/never_inline"错误处理技术的最佳方法是什么?
- 在 c++ 中对类中的 c 字符串动态数组进行排序的最佳方法是什么?
- 在AVX通道中混洗的最佳方式
- 程序顶部的声明与定义(最佳实践)
- 别名模板的专业化 C++11 中没有开销的最佳替代方案