问题标签 [structural-typing]
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.
language-design - 鸭子打字,必须是动态的吗?
维基百科曾经说过*关于鸭子打字:
在使用面向对象编程语言的计算机编程中,鸭子类型是一种动态类型,其中对象的当前方法和属性集确定有效语义,而不是从特定类或特定接口的实现继承。
(* 编者注:自发布此问题以来,维基百科文章已被编辑以删除“动态”一词。)
它说的是结构类型:
结构类型系统(或基于属性的类型系统)是类型系统的主要类,其中类型兼容性和等价性由类型的结构决定,而不是通过显式声明。
它将结构子类型与鸭子类型进行对比:
[结构系统] 与 ... 鸭子类型形成对比,其中只检查在运行时访问的结构部分的兼容性。
然而,在我看来, duck-typing一词至少直观地包含了结构子类型系统。事实上维基百科说:
概念的名称 [duck-typing] 指的是鸭子测试,归因于 James Whitcomb Riley,它可以表述如下:“当我看到一只鸟儿像鸭子一样走路、像鸭子一样游泳、像鸭子一样嘎嘎叫时,我称那只鸟为鸭子。”
所以我的问题是:为什么我不能将结构子类型称为鸭子类型?是否甚至存在不能被归类为鸭子类型的动态类型语言?
后记:
正如 reddit.com 上一个叫daydreamdrunk的人如此雄辩地说: “如果它像鸭子一样编译并像鸭子一样链接......”
后记
许多答案似乎基本上只是重复我在这里已经引用的内容,而没有解决更深层次的问题,这就是为什么不使用术语鸭子类型来涵盖动态类型和结构子类型?如果您只想谈论鸭子类型而不是结构子类型,那么就称它为:动态成员查找。我的问题是,鸭子打字这个词对我没有任何意义,这只适用于动态语言。
scala - Scala 中的模式匹配结构类型
为什么这会打印 wtf?模式匹配对结构类型不起作用吗?
c# - C# 中泛型类型的命名空间范围别名
让我们举个例子:
编译器说:
无法从用法中推断方法“System.Linq.Enumerable.Select(System.Collections.Generic.IEnumerable, System.Func)”的类型参数。尝试明确指定类型参数。
这是因为,它无法转换Bar
为Func<IList<X>, int, IDictionary<Y, IList<Z>>>
.
如果我可以在 C# 中为泛型类型创建类型命名空间范围的类型别名,那就太好了。然后我不会将其定义Bar
为委托,而是将其定义为Func<IList<X>, int, IDictionary<Y, IList<Z>>>
.
然后我还可以为 eg 定义命名空间范围的别名IDictionary<Y, IList<Z>>
。
如果使用得当:),它将使代码更具可读性。现在,我必须内联泛型类型,而真正的代码可读性不好:(
你有没有遇到同样的麻烦:)?有什么好的理由为什么它不在 C# 3.0 中?或者没有充分的理由,只是金钱和/或时间的问题?
编辑:我知道我可以使用using
,但它不是命名空间范围内的 - 对我来说不太方便。
EDIT2:参见Joren 的评论,他建议结构类型也可以解决问题。
scala - 将 Scala 结构类型与抽象类型一起使用
我正在尝试定义一个结构类型,定义任何具有“add”方法的集合(例如,java 集合)。使用它,我想定义一些对某个集合进行操作的高阶函数
这不会编译并出现以下错误
我尝试删除 GenericCollection 上的参数并将其放在方法上:
但我得到另一个错误:
谁能给我一些关于如何在 Scala 中使用带有抽象类型参数的结构类型的建议?或者如何实现我想要实现的目标?非常感谢!
c# - C# 是否具有与 Scala 的结构类型等价的功能?
在 Scala 中,我可以如下定义结构类型:
type Pressable = { def press(): Unit }
这意味着我可以定义一个函数或方法,它以可按下的东西作为参数,如下所示:
def foo(i: Pressable) { // etc.
我传递给该函数的对象必须为它定义了一个名为 press() 的方法,该方法与类型中定义的类型签名相匹配 - 不接受任何参数,返回 Unit(Scala 的 void 版本)。
我什至可以使用内联结构类型:
def foo(i: { def press(): Unit }) { // etc.
它基本上允许程序员拥有鸭子类型的所有好处,同时仍然具有编译时类型检查的好处。
C#有类似的东西吗?我在 Google 上搜索过,但找不到任何东西,但我对 C# 并不熟悉。如果没有,有没有计划添加这个?
c++ - C++ 或任何其他语言中的可选结构类型的可能性?
在 C++ 中如何告诉编译器 Ogre::Vector3 IS_SAME_AS SomeOtherLIB::Vector3 ?我觉得..在像 c++ 这样不是结构类型的语言中,但在某些情况下它是有意义的。
通常作为游戏开发人员使用 4+ 提供排序或他们自己的 Vector3 实现的库时。代码中充斥着 ToOgre、ToThis、ToThat 转换函数。那是很多 Float3 复制,首先不应该发生。
在 C++ 或任何其他语言中,我们不必将一种类型转换(复制)到另一种类型,这本质上是相同的。但是 C++ 中的任何解决方案,因为大多数优秀的 gamedevs 库都是用于 c/c++ 的。
scala - Scala - 如何定义引用自身的结构类型?
我正在尝试编写一个通用interpolate
方法,该方法适用于具有两个方法 a*
和 a 的任何类型+
,如下所示:
这不起作用(在 Scala 2.8.0.RC7 上),我收到以下错误消息:
如何正确指定结构类型?(或者有更好的方法吗?)
scala - Scala 中的广义结构类型一致性
我对使特定类型符合更一般的结构类型的问题感兴趣。考虑以下示例:
在每一种不符合要求的情况下,对 in 方法的调用都General
可以安全地解析为 in 中的相应方法Specific
。在这个问题中可以找到一个更有趣的实际示例:
这里,Customer 的copy
方法不符合 Versionable 的 self-type annotation 中的签名。但是请注意,如果编译器允许,copy
可以像在Versionable.incrementVersion
. 显然,Customercopy
方法的实际签名对于在 Versionable 中使用来说太具体了,因为它带有不相关的知识,即可以选择提供name
参数。
有没有办法解决这些限制?有没有理由认为这种普遍的一致性是一个坏主意?
scala - 为什么结构类型的编译时生成技术会阻止单独编译?
我正在阅读(好的,略读) Dubochet 和 Odersky 的Compiling Structural Types on the JVM,并对以下声明感到困惑:
生成技术创建 Java 接口来代替 JVM 上的结构类型。这种技术的复杂性在于,在程序中任何地方用作结构类型的所有类都必须实现正确的接口。当这在编译时完成时,它会阻止单独编译。
(重点补充)
考虑论文中的自动关闭示例:
我们不能为该Closeable
类型生成一个接口,如下所示:
并将我们的定义转换autoclose
为
然后考虑一个呼叫站点autoclose
:
由于fis
is a FileInputStream
,它没有实现AnonymousInterface1
,我们需要生成一个包装器:
我一定错过了什么,但我不清楚它是什么。为什么这种方法会阻止单独编译?
scala - 关于 Scala 中(递归)结构类型的有趣观察
我需要在某些代码中使用带有特征和结构类型作为类型参数约束的一些递归结构类型。它工作得很好,但后来我了解到 Scala 不支持递归结构类型。
所以有人可以解释一下为什么这很好用:
这不是: