这就是我现在正在做的事情:
private var accounts = Vector.empty[Account]
def removeAccount(account: Account)
{
accounts = accounts.filterNot(_ == account)
}
有没有更易读的解决方案?理想情况下,我想写accounts = accounts.remove(account)
.
这就是我现在正在做的事情:
private var accounts = Vector.empty[Account]
def removeAccount(account: Account)
{
accounts = accounts.filterNot(_ == account)
}
有没有更易读的解决方案?理想情况下,我想写accounts = accounts.remove(account)
.
不幸的是没有,更糟糕的是(也许),如果同一个帐户出现两次,filterNot
将删除它们。我唯一能提供的可读性就是使用
accounts.filter(_ != account)
另一种可能性是使用具有删除操作的集合类型,例如 a TreeSet
(它被称为-
)。如果您无论如何都没有重复的条目,那么 aSet
完全可以。(当然,对于某些操作来说它比较慢,但它可能更适合应用程序——它在删除单个条目时更有效;filterNot
你基本上必须重新构建整个条目Vector
。)
我会用这个:
accounts filterNot account.==
这对我来说读起来很好,但是ymmv。我也想要一个count
不带谓词的,但是集合库确实缺乏专门的方法,其中一个带有谓词的方法可以概括操作。
在 2.8.x 之前,由于语义问题,有一种方法 iirc 被弃用了。-
如果我的记忆对我有用,它实际上可能会在 2.10 恢复,但事实并非如此。编辑:我检查了它,发现它-
现在保留给一个可变方法,该方法修改它所应用的集合。我完全赞成-:
/:-
尽管在序列上,在其中删除第一个或最后一个元素等于某物是有意义的。有人愿意为此买票吗?我会赞成。:-)
你可以这样做:
def removeFirst[T](xs: Vector[T], x: T) = {
val i = xs.indexOf(x)
if (i == -1) xs else xs.patch(i, Nil, 1)
}
然后
accounts = removeFirst(accounts, account)
不过,我认为问题的关键在于 aVector
可能不是您想要取出的一组Set
项目的正确集合类型(提示:try )。如果您想对 ID 或插入索引进行索引,那么Map
可能就是您所追求的(它确实有一个-
方法)。如果你想有效地索引多个事物,你需要一个数据库!
您可以使用diff
为所有序列定义的方法。它计算两个序列之间的多重集差异 - 这意味着它将根据需要删除尽可能多的元素。
Vector(1, 2, 1, 3, 2).diff(Seq(1)) =>
Vector(2, 1, 3, 2)
Vector(1, 2, 1, 3, 2).diff(Seq(1, 1)) =>
Vector(2, 3, 2)
Vector(1, 2, 1, 3, 2).diff(Seq(1, 1, 2))
Vector(3, 2)
如果你不想使用filterNot
闭包,你可以使用更详细但更明确的理解风格。
private var accounts = Vector.empty[Account]
def removeAccount(account: Account)
{
accounts = for { a <- accounts
if a != account } yield { a }
}
在这种情况下是否感觉更好,这是个人喜好问题。
当然,对于涉及嵌套 flatMaps 等的更复杂的表达式,我同意 Martin Odersky 的建议,即 for-comprehensions 可以更容易阅读,尤其是对于新手而言。