问题标签 [double-dispatch]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
c++ - 没有 RTTI 的 C++ 双分派“可扩展”
有谁知道在 C++ 中不使用 RTTI 和 dynamic_cast<> 正确处理双重调度的方法,还有一个解决方案,其中类层次结构是可扩展的,即基类可以进一步派生,其定义/实现不需要知道吗?
我怀疑没有办法,但我很高兴被证明是错误的:)
c++ - Equals() 的 C++ 双重调度
想象一下,我有抽象基类 Shape
、派生类Circle
和Rectangle
.
Shape*
假设我有两个指针,我需要确定两个形状是否相等。(这是因为我有两个实例,vector<Shape*>
我想看看它们是否具有相同的形状。)
推荐的方法是双重调度。我想出的是这个(这里大大简化了,所以形状等于所有其他相同类型的形状):
这可行,但我必须为每个派生类添加一个单独的equals
函数和friend
声明。Shape
然后我也必须将完全相同的equals
函数复制粘贴到每个派生类中。这是一个非常多的样板,比如 10 种不同的形状!
有没有更简单的方法来做到这一点?
dynamic_cast
是不可能的;太慢了。(是的,我对其进行了基准测试。速度在我的应用程序中很重要。)
我试过这个但它不起作用:
equals()
即使在相同的形状上,也总是返回 false。is_equal(Shape&)
即使有“更具体的”匹配可用,调度似乎总是选择基本功能。这可能是有道理的,但我对 C++ 调度的理解不够深入,无法知道原因。
c++ - C++ 中 InputMap 的双重调度失败 - 代码简化为
您好,在我当前的一个项目中,我想实现一个 InputMap。所以我有一个抽象的输入
和一个 InputMap
到目前为止一切顺利 - 这里没有功能。现在我从我的抽象输入类中派生出我的第一个真实输入:
这是我派生的 InputMap
这是测试:
当然我希望input.Dispatch(&map)
调用map.HandleInput(StringInput input)
,但不幸的是总是调用默认处理程序。我对这个模式编程错了吗?谢谢大家,我一直在盯着我的代码,但我没有看到它。
c++ - c++ 双调度观察者通知
这是我目前正在排除故障的代码:
所以代码运行,CTimer::notify()
被调用,它创建 aTimerNotification
并将其传递给观察者,观察者readNotification()
又通过它调用通知的read()
方法,最后调用观察者的(希望)正确的update()
方法。
最后一步是失败的。它调用update(INotification&)
方法而不是所需的update(ITimerNotification&)
方法。
为了使这种尝试的双重调度模式起作用,我在这里缺少什么?它似乎没有获得正确的类型信息来选择适当的函数调用。
谢谢你的帮助!
scala - 如何在不使用 switch 语句的情况下根据两个对象的类型在 Scala/Java 中调用正确的方法?
我目前正在 Scala 中开发一款游戏,其中有许多实体(例如 GunBattery、Squadron、EnemyShip、EnemyFighter),它们都继承自 GameEntity 类。游戏实体通过事件/消息系统向游戏世界和彼此广播感兴趣的事物。有许多 EventMesssage(EntityDied、FireAtPosition、HullBreach)。
目前,每个实体对于它响应的每种消息类型(例如)都有一个receive(msg:EventMessage)
以及更具体的接收方法。receive(msg:EntityDiedMessage)
通用receive(msg:EventMessage)
方法只是一个 switch 语句,它根据消息的类型调用适当的接收方法。
随着游戏的开发,实体和消息的列表(以及哪些实体将响应哪些消息)是流动的。理想情况下,如果我希望游戏实体能够接收新的消息类型,我只想能够编写响应的逻辑,而不是这样做并且必须在其他地方更新匹配语句。
我的一个想法是将接收方法从游戏实体层次结构中提取出来并具有一系列函数,例如def receive(e:EnemyShip,m:ExplosionMessage)
和 defreceive(e:SpaceStation,m:ExplosionMessage)
但这使问题更加复杂,因为现在我需要一个匹配语句来涵盖消息和游戏实体类型。
这似乎与双重和多重调度的概念以及访问者模式有关,但我在理解它时遇到了一些麻烦。我并不是在寻找 OOP 解决方案本身,但是如果可能的话,我想避免反思。
编辑
做一些更多的研究,我认为我正在寻找类似于 Clojure 的东西defmulti
。
您可以执行以下操作:
java - 设计模仿访客没有缺点
我正在寻找一种简洁的设计来模拟访客功能,而没有它所具有的许多缺点。在 Java 中,传统的实现(如 GoF 中所述)采用双重调度来摆脱 if-else。为了解决这个问题,我看到了一些使用反射来避免修改“Visitable”类的实现,但是这些实现在查找方法名称时依赖于硬编码的字符串。虽然很有用,但我仍然认为它们不是干净的设计。
是否可以使用数据结构和/或良好的 OO 设计来模拟相同的想法?它不一定是模式,只是我正在寻找解决类似问题的示例(例如:使用 a Map<Class<T>,SomeFunctionObject>
)。
更新是这样的:
我认为实际上是模板模式和命令模式的混合。随时发表您对如何增强它的建议。
architecture - (嵌套?)多次调度 [访客模式]
我的应用程序架构遇到了障碍。我刚刚开始使用访问者模式在运行时我不知道的抽象对象上执行特定的算法。我的问题是我的算法也取决于嵌套抽象类型的类型。
让我说明一下我的意思:
我有一个抽象的 DataSource 类。由此我实现了具体的 DataSourceReference 和 DataSourceExplicit 类。我还有一个抽象的报告类(反序列化的元数据),我从中实现了具体的报告类 ReportTypeA 和 ReportTypeB。创建这些对象时,它们的 DataSource 可以是任何扩展的 DataSource 类。
我需要两者,实际的 Report 类型和 DataSource 类型,以便我可以相应地执行。我可以使用访问者模式获得一致的报告类型,但不知道如何为 DataSource 做同样的事情。
访问 Report 后我无法访问 DataSource,因为我会丢失 Report 的具体类型(因为您必须让它接受基本 Report 类型:Accept(SomeDataSourceVisitor d, MetaReport m) - 或对每种可能的 Report 类型进行重载,这违背了访问者模式的目的。看到我的问题了吗?
有任何想法吗?我想远离使用动态,因为它不需要新报告类型的开发人员来确保调度程序(访问者)支持新报告。
当前代码:
c# - 双重调度和替代方案
我试图找到一种更好的方法来处理一些不断增长的if
构造来处理不同类型的类。这些类最终是不同值类型(int、DateTime 等)的包装器,并带有一些额外的状态信息。因此,这些类之间的主要区别在于它们包含的数据类型。虽然它们实现了泛型接口,但它们还需要保存在同构集合中,因此它们还实现了非泛型接口。类实例根据它们所代表的数据类型进行处理,并且它们的传播继续或不继续基于此。
虽然这不一定是 .NET 或 C# 问题,但我的代码是用 C# 编写的。
示例类:
我提出了两个选择:
双重派送
我最近了解了访问者模式及其使用双重调度来处理这种情况。这很有吸引力,因为它允许不想要的数据不传播(如果我们只想处理一个 int,我们可以以不同于 DateTime 的方式处理它)。此外,如何处理不同类型的行为将仅限于处理调度的单个类。但是如果/当必须支持新的值类型时,需要进行相当多的维护。
联合班
包含支持的每种值类型的属性的类可能是这些类中的每一个存储的内容。对值的任何操作都会影响相应的组件。这比双分派策略更简单,维护更少,但这意味着每条数据都会不必要地传播,因为你不能再按照“我不对那种数据类型进行操作”来区分”。但是,如果/当需要支持新类型时,它们只需要进入此类(加上需要创建以支持新数据类型的任何其他类)。
有更好的选择吗?这两个选项中是否有我认为我不应该考虑的东西?
design-patterns - 访客模式和双重调度之间的区别
我正在阅读有关访问者模式的信息,它看起来与 Double Dispatch 相同。两者有没有区别。做这两个词的意思是一样的。
参考: http: //www.vincehuston.org/dp/visitor.html