是否有一个简单而有效的解决方案来确定Scala Iterable的前n个元素?我的意思是
iter.toList.sortBy(_.myAttr).take(2)
Run Code Online (Sandbox Code Playgroud)
但是当只有前2名感兴趣时,无需对所有元素进行排序.理想情况下,我正在寻找类似的东西
iter.top(2, _.myAttr)
Run Code Online (Sandbox Code Playgroud)
另请参阅:使用Ordering的顶部元素的解决方案:在Scala中,如何使用List.min或List.max订购[T]并保持代码可读
谢谢大家的解决方案.最后,我采用了用户未知的原始解决方案并使用它Iterable
和pimp-my-library模式:
implicit def iterExt[A](iter: Iterable[A]) = new {
def top[B](n: Int, f: A => B)(implicit ord: Ordering[B]): List[A] = {
def updateSofar (sofar: List [A], el: A): List [A] = {
//println (el + " - " + sofar)
if (ord.compare(f(el), f(sofar.head)) > 0)
(el :: sofar.tail).sortBy (f)
else sofar
}
val (sofar, rest) = iter.splitAt(n)
(sofar.toList.sortBy (f) /: rest) (updateSofar (_, _)).reverse
}
} …
Run Code Online (Sandbox Code Playgroud) 我怎么能压制"匹配并不详尽!" 以下Scala代码中的警告?
val l = "1" :: "2" :: Nil
l.sliding(2).foreach{case List(a,b) => }
Run Code Online (Sandbox Code Playgroud)
到目前为止,我发现的唯一解决方案是使用其他匹配语句包围模式匹配:
l.sliding(2).foreach{x => (x: @unchecked) match {case List(a,b) => }}
Run Code Online (Sandbox Code Playgroud)
然而,这使得代码不必要地复杂且难以理解.所以必须有一个更短,更可读的替代方案.有人知道吗?
我忘了提到我的列表l
在我的程序中至少有2个元素.这就是为什么我可以安全地压制警告.
我正在寻找Scala中的FIFO流,即提供功能的东西
流应该是可关闭的,并且应该阻止访问下一个元素,直到添加元素或关闭流.
实际上我有点惊讶的是,集合库没有(似乎)包含这样的数据结构,因为IMO是一个非常经典的数据结构.
我的问题:
1)我忽略了什么吗?是否已有提供此功能的课程?
2)好的,如果它没有包含在集合库中,那么它可能只是现有集合类的一个简单组合.但是,我试图找到这个简单的代码,但对于这样一个简单的问题,我的实现看起来仍然非常复杂.这样的FifoStream有更简单的解决方案吗?
class FifoStream[T] extends Closeable {
val queue = new Queue[Option[T]]
lazy val stream = nextStreamElem
private def nextStreamElem: Stream[T] = next() match {
case Some(elem) => Stream.cons(elem, nextStreamElem)
case None => Stream.empty
}
/** Returns next element in the queue (may wait for it to be inserted). */
private def next() = {
queue.synchronized {
if (queue.isEmpty) queue.wait()
queue.dequeue()
}
}
/** Adds new elements to this stream. */
def …
Run Code Online (Sandbox Code Playgroud)我正在研究一种基于Scala的脚本语言(内部DSL),它允许用户在Scala脚本文件中定义多个数据转换函数.由于这些功能的应用可能需要几个小时,我想将结果缓存在数据库中.允许用户更改转换函数的定义以及添加新函数.但是,然后用户使用略微修改的脚本重新启动应用程序,我只想执行已更改或添加的那些功能.问题是如何检测这些变化?为简单起见,我们假设用户只能调整脚本文件,以便可以假定对此脚本中未定义的内容的任何引用都不会更改.
在这种情况下,检测此类用户定义函数的更改的最佳实践是什么?
到现在为止我虽然:
然而,这三种方法都存在缺陷.
有人有这些"解决方案"的经验或者可以建议我更好吗?
我想使用返回类型R的单个函数映射Scala元组(或三元组......)的元素.结果应该是元组类型为R的元组(或三元组......).
好的,如果元组的元素来自同一类型,则映射不是问题:
scala> implicit def t2mapper[A](t: (A,A)) = new { def map[R](f: A => R) = (f(t._1),f(t._2)) }
t2mapper: [A](t: (A, A))java.lang.Object{def map[R](f: (A) => R): (R, R)}
scala> (1,2) map (_ + 1)
res0: (Int, Int) = (2,3)
Run Code Online (Sandbox Code Playgroud)
但是,是否也可以使这个解决方案通用,即以相同的方式映射包含不同类型元素的元组?
例:
class Super(i: Int)
object Sub1 extends Super(1)
object Sub2 extends Super(2)
(Sub1, Sub2) map (_.i)
Run Code Online (Sandbox Code Playgroud)
应该回来
(1,2): (Int, Int)
Run Code Online (Sandbox Code Playgroud)
但我找不到解决方案,以便映射函数确定Sub1和Sub2的超类型.我试图使用类型边界,但我的想法失败了:
scala> implicit def t2mapper[A,B](t: (A,B)) = new { def map[X >: A, X >: B, R](f: X => R) …
Run Code Online (Sandbox Code Playgroud) IDEA或其中一个插件是否能够将代码与特殊字符对齐?
我的意思是代码
Map(
'name -> "Peter",
'age -> 27,
'company -> "Foobar"
)
Run Code Online (Sandbox Code Playgroud)
变成了
Map(
'name -> "Peter",
'age -> 27,
'company -> "Foobar"
)
Run Code Online (Sandbox Code Playgroud)
例2:
execute("x", true, 27)
execute("foobar", false, 0)
Run Code Online (Sandbox Code Playgroud)
变成了
execute("x" , true , 27)
execute("foobar", false, 0 )
Run Code Online (Sandbox Code Playgroud) 我想定义一个名称Ext
,它将现有equals
方法重命名为,equalsByAttributes
并同时定义一个新equals
方法.该特征用于扩展案例类.我目前的解决方案看起来有点hacky:
case class A(id: Int) extends Ext
trait Ext { p: Product =>
// new implementation
override def equals(obj: Any) = obj match {
case that: AnyRef => this eq that
case _ => false
}
// reimplementation of old equals implementation
def equalsByAttributes(obj: Any) = obj match {
case that: Product =>
if (this.getClass.isAssignableFrom(that.getClass) || that.getClass.isAssignableFrom(this.getClass))
p.productIterator.toList == that.productIterator.toList
else
false
case _ => false
}
}
Run Code Online (Sandbox Code Playgroud)
我不知道是否有引用一个直接的方式A
的equals …
我想以编程方式在运行时确定Scala类的所有属性.例如,对于下面的Scala类,我想确定方法name1
,name3
,name4
,和name5
是为干将的性质A
:
class A(val name1: String, private val name2: String) {
val name3 = ""
var name4 = ""
def name5 = ""
def name6() = ""
}
Run Code Online (Sandbox Code Playgroud)
大多数工作都可以使用Java的反射API完成.遗憾的是我没能检测之间的差异name5
和name6()
.因此,我开始使用ScalaSigParser下一个试验,但ScalaSig的标志对name5
和name6()
是不幸的也是相同的.这是我的代码:
def gettersOf(clazz: Class[_]) = {
for (ssig <- ScalaSigParser.parse(clazz))
yield {
ssig.symbols.toList.collect{
case m: MethodSymbol => m
}.filter(m => (m.symbolInfo.flags & 0xFFFFF) == 0x200)
}
}
gettersOf(classOf[A]).get.foreach{m =>
println(m.name + ": " + m) …
Run Code Online (Sandbox Code Playgroud) scala ×8
algorithm ×1
bytecode ×1
case-class ×1
fifo ×1
java ×1
queue ×1
reflection ×1
runtime ×1
stream ×1
superclass ×1
tuples ×1