我对Scala和整个函数式编程风格都很陌生.我需要做的是通过比较两个单词的每个字母来计算两个字符串之间的相似性.该函数将与相同长度的单词一起使用.
例如,"网络"和"锻炼"将具有相似度1."House"和"Mouse"将具有4的相似度.
这是我如何用一种非常老式的C#方式做到的:
int calculateCharSimilarity(string first, string second)
{
int similarity = 0;
for(int i = 0; i < first.lenght() && i < first.lenght(); i++)
{
if(first.charAt(i) == second.charAt(i))
similarity++;
}
return similarity;
}
Run Code Online (Sandbox Code Playgroud)
到目前为止我在scala中所做的是编写一个尾递归函数以避免循环:
@tailrec
private def calculateCharSimilarity(first: Seq[Char], second: Seq[Char], similarity: Int = 0): Int = {
if(first != Nil && second != Nil)
calculateCharSimilarity(first.tail, second.tail, if(first.head == second.head) similarity + 1 else similarity)
else
similarity
}
Run Code Online (Sandbox Code Playgroud)
但我不确定这是否是Scala的最佳实践.有没有什么方法可以使用Collection Combinators(zip,filter)更优雅?
我正在使用PlayFramework 2.5.3,并希望创建akka.stream.scaladsl.Source一个akka.event.EventStream(事件流是演员系统的一部分).事件流将产生来自某种类型的事件,因此我需要订阅该特定类型的事件并通过使用来推送它们play.api.mvc.Results.chunked.有没有简单的方法来创建这样的Source使用Akka Streams 2.4.5?
scala playframework server-sent-events reactive-streams akka-stream
我想要一个函数接收Iterable并返回一个带有加权对象的新函数Iterable.
让我举个例子:
对象类(我们称之为Weight)具有一个Int名为的值times:
class Weight(val times: Int)
Run Code Online (Sandbox Code Playgroud)
最初Iterable有四个要素:{a, b, c, d}.权重如下:
结果迭代将是= {a, a, a, b, c, c, d, d}.
到目前为止,我的实现非常难看:
def weightedIteration(initial: Iterable[Wheight]): Iterable[Weight] = {
var list: List[Weight] = Nil
initial.foreach(weight => {
for(_ <- 0 until weight.times)
list :+= weight
})
list
}
Run Code Online (Sandbox Code Playgroud)
我真的不喜欢的是var列表.我宁愿让每个元素产生所需的次数.我试图将yield语句放入for表达式; 但是效果不好,因为这个方法中的最后一个语句是foreach表达式返回a Unit.
在这种情况下,有没有办法使用收益率?或者从一些Collection Combinator(map)中返回一个iterable?只要我摆脱var列表,我不介意任何一种方式.