我理解Ruby和Python的优点。Scala的yield是做什么的?
当前回答
val aList = List( 1,2,3,4,5 )
val res3 = for ( al <- aList if al > 3 ) yield al + 1
val res4 = aList.filter(_ > 3).map(_ + 1)
println( res3 )
println( res4 )
这两段代码是等价的。
val res3 = for (al <- aList) yield al + 1 > 3
val res4 = aList.map( _+ 1 > 3 )
println( res3 )
println( res4 )
这两段代码也是等价的。
Map和yield一样灵活,反之亦然。
其他回答
它用于序列推导式(就像Python的列表推导式和生成器一样,在这里你也可以使用yield)。
它与for结合应用,并将一个新元素写入结果序列。
简单示例(来自scala-lang)
/** Turn command line arguments to uppercase */
object Main {
def main(args: Array[String]) {
val res = for (a <- args) yield a.toUpperCase
println("Arguments: " + res.toString)
}
}
f#中对应的表达式为
[ for a in args -> a.toUpperCase ]
or
from a in args select a.toUpperCase
在Linq中。
Ruby的产量有不同的影响。
除非你能从Scala用户那里得到更好的答案(我不是),以下是我的理解。
它仅作为以for开头的表达式的一部分出现,该表达式说明如何从现有列表生成新列表。
喜欢的东西:
var doubled = for (n <- original) yield n * 2
因此,每个输入都有一个输出项(尽管我相信有一种方法可以删除重复项)。
这与yield在其他语言中所支持的“命令式延续”有很大不同,在其他语言中,它提供了一种方法,可以从一些具有几乎任何结构的命令式代码生成任意长度的列表。
(如果你熟悉c#,它更接近LINQ的选择操作符,而不是yield return)。
为了理解,考虑以下内容
val A = for (i <- Int.MinValue to Int.MaxValue; if i > 3) yield i
大声读出来可能会有帮助
对于每一个整数i,如果它大于3,那么yield (produce) i并将其添加到列表a中。
在数学集合构建符号方面,上面的for-comprehension类似于
这可以理解为
"对于每一个整数,如果它大于,那么它就是集合中的成员"
或者作为替代
"是所有整数的集合,每个都大于"
Yield类似于for循环,它有一个我们看不到的缓冲区,对于每一个增量,它都会不断向缓冲区中添加下一项。当for循环结束运行时,它将返回所有产生值的集合。Yield可以用作简单的算术运算符,甚至可以与数组结合使用。 为了更好地理解,这里有两个简单的例子
scala>for (i <- 1 to 5) yield i * 3
res: scala.collection.immutable。IndexedSeq[Int] = Vector(3,6,9,12,15)
scala> val nums = Seq(1,2,3)
nums: Seq[Int] = List(1, 2, 3)
scala> val letters = Seq('a', 'b', 'c')
letters: Seq[Char] = List(a, b, c)
scala> val res = for {
| n <- nums
| c <- letters
| } yield (n, c)
res: Seq [(Int、Char)] =列表((1),(b)、(1 c), (2), (2 b), (2 c), (3), (b)、(3 c))
希望这能有所帮助!!
是的,正如Earwicker所说,它几乎等同于LINQ的select,与Ruby和Python的yield关系不大。基本上,在c#中你会写
from ... select ???
而在Scala中则相反
for ... yield ???
同样重要的是要理解for推导式不仅适用于序列,还适用于任何定义了特定方法的类型,就像LINQ:
如果你的类型只定义map,它允许由 单独的发电机。 如果它定义了flatMap和map,则允许for-expression组成 几个发电机。 如果定义了foreach,则允许for循环而不产生yield(单个和多个生成器都可以)。 如果它定义了filter,则允许以If开头的for-filter表达式 在for表达式中。
推荐文章
- 我如何用groupBy计算发生的事件?
- 定义一个函数时,“def”和“val”有什么区别
- 在Scala中获取列表中的项目?
- 在函数式编程中,什么是函子?
- case对象和对象的区别
- Scala中的Case对象与枚举
- 面向对象编程,函数式编程,过程式编程
- 任务不可序列化:java.io.NotSerializableException,当只对类而不是对象调用闭包外部的函数时
- 在Scala中将一个元素附加到列表的末尾
- 在Scala中按名称调用vs按值调用,需要澄清
- 解析命令行参数的最佳方法?
- Android Scala编程
- 为什么不可变性在JavaScript中如此重要(或需要)?
- lazy val做什么?
- Scala:抽象类型vs泛型