我最近遇到了一个非常有趣的网站,表达了一个非常有趣的想法 - 反竞选活动.您可以在www.antiifcampaign.com上看到这一点.我必须同意复杂的嵌套IF语句是后方的绝对痛苦.我目前正在进行一个项目,直到最近才有一些疯狂的嵌套IF向右滚动相当多的方式.我们以两种方式解决了问题 - 我们使用Windows Workflow Foundation来解决路由(或工作流程)问题.我们正在利用ILOG Rules for .NET(最近由IBM购买!!)实施所有业务规则.这在很大程度上已经治愈了我们的嵌套IF痛苦...但我发现自己想知道有多少人以AntiIfCampaign的优秀人士建议的方式(通过这里看到一个例子)通过创建大量抽象类来解决他们的痛苦表示最初由嵌套IF覆盖的给定方案.我想知道解决这种复杂性的另一种方法是否也可能是使用诸如StructureMap之类的IoC容器来移入和移出不同的功能.无论哪种方式...
问题: 给定一个场景,我有一个嵌套的复杂IF或SWITCH语句,用于评估给定类型的事物(比如评估一个枚举),以确定我想如何通过枚举类型处理该事物的处理 - 有什么一些如何在不使用IF或SWITCH分层结构的情况下进行相同形式的处理?
public enum WidgetTypes
{
Type1,
Type2,
Type3,
Type4
}
...
WidgetTypes _myType = WidgetTypes.Type1;
...
switch(_myType)
{
case WidgetTypes.Type1:
//do something
break;
case WidgetTypes.Type2:
//do something
break;
//etc...
}
Run Code Online (Sandbox Code Playgroud)
Ed *_* S. 59
问题不在于'if'语句,而是编写错误代码的程序员.
编辑:另外,正如其他人所指出的,当你使用if语句来检查对象的类型时,你应该使用多态(如果可用),但是if语句本身是非常有用和基本结构.
小智 35
在Java中,很容易将枚举用作多态反if代理.
public class AntiIf {
public enum WidgetTypes {
Type1 {
public void doSomething() {
//...
}},
Type2 {
public void doSomething() {
//...
}},
Type3 {
public void doSomething() {
//...
}},
Type4 {
public void doSomething() {
//...
}};
public abstract void doSomething();
}
WidgetTypes _myType; // set by someone to one of the types.
public void someFunction() {
//...
_myType.doSomething();
//...
}
}
Run Code Online (Sandbox Code Playgroud)
Dar*_*ryl 23
反对如果是愚蠢的.
有时替换条件via多态是正确的做法,但在那些情况下,if语句不是真正的问题.真正的问题是以非抽象方式处理抽象类型,即未能在基类的抽象层次上进行思考.
其他时候可以替换条件via多态,但这样做是个坏主意.导致您将一种类型与另一种类型区别对待的逻辑可能属于算法本身,而不属于单个类.将该逻辑移动到类可能会导致类的代码过度地意识到使用它们的上下文.
但大多数情况下,if语句与多态无关.摆脱if语句是错误的目标.
反对如果是愚蠢的.
Mar*_*age 14
切换语句通常可以用多态替换:
abstract class WidgetBase {
public abstract void DoSomething();
}
class Widget1 : WidgetBase {
public override void DoSomething() {
// Do something ...
}
}
class Widget2 : WidgetBase {
public override void DoSomething() {
// Do something ...
}
}
...
Widget widget = new Widget1(); // Use a factory pattern instead.
widget.DoSomething();
Run Code Online (Sandbox Code Playgroud)
IRB*_*BMe 12
您可以使用命令模式根据某些值或输入执行命令.
在回答你的问题时,你可以使用一个简单的查找表或多态来实现这一点,虽然它将逻辑放在程序的不同部分,这可能确实是正确的事情.以下是C#中的几个示例:
var commands = new Dictionary<WidgetTypes, Action>()
{
{ WidgetTypes.Type1, () => Console.WriteLine("Type 1") },
{ WidgetTypes.Type2, () => Console.WriteLine("Type 2") },
{ WidgetTypes.Type3, () => Console.WriteLine("Type 3") },
{ WidgetTypes.Type4, () => Console.WriteLine("Type 4") }
};
commands[WidgetTypes.Type1]();
Run Code Online (Sandbox Code Playgroud)
public interface ICommandHandler
{
void HandleCommand();
}
public class Command1Handler : ICommandHandler
{
public void HandleCommand()
{
Console.WriteLine("Type 1");
}
}
// ...
var commands = new Dictionary<WidgetTypes, ICommandHandler>()
{
{ WidgetTypes.Type1, new Command1Handler() },
{ WidgetTypes.Type2, new Command2Handler() },
{ WidgetTypes.Type3, new Command3Handler() },
{ WidgetTypes.Type4, new Command4Handler() }
};
commands[WidgetTypes.Type1].HandleCommand();
Run Code Online (Sandbox Code Playgroud)
以及一个奖励反射方法,用于调用具有相同名称的当前对象上的方法:
public void Type1()
{
Console.WriteLine("Type 1");
}
//...
var type = WidgetTypes.Type2;
typeof(MyClass).GetMethod(type.ToString()).Invoke(this, new object[] { });
Run Code Online (Sandbox Code Playgroud)
注意:实际上并不这样做
...什么?
没有某种比较,我无法想象如何做这样的事情.完全没有.
我可以想象一个反goto运动,但如果看起来像一个非常该死的控制流程结构给我.
不要担心简单的if语句或直接的switch语句.
担心这个:
| 归档时间: |
|
| 查看次数: |
14848 次 |
| 最近记录: |