我正在尝试编写惯用的scala代码来遍历两个列表列表,并生成一个仅包含两个列表差异的新列表。
在程序Scala中我会做这样的事情:
val first: List[List[Int]] = List(List(1,2,3,4,5),List(1,2,3,4,5), List(1,2,3,4,5))
val second: List[List[Int]] = List(List(1,2,3,4,5),List(1,23,3,45,5),List(1,2,3,4,5))
var diff: List[String] = List[String]()
for (i <- List.range(0, first.size)){
for (j <- List.range(0, first(0).size)){
println(first(i)(j) + " " + second(i)(j))
if (first(i)(j) != second(i)(j)) diff = diff ::: (s"${second(i)(j)}" :: Nil)
}
}
当然我不喜欢这个,我试图用理解来写一个解决方案,但没有成功。
我能得到的最接近的是:
for {(lf,ls) <- (first zip second) } yield if (lf == ls) lf else ls
但是从理解中我无法生成与输入类型不同的String列表。
有什么建议吗?
答案 0 :(得分:3)
惯用的Scala会是这样的:
(
for {
(row1, row2) <- (first, second).zipped // go through rows with the same index
(value1, value2) <- (row1, row2).zipped // go through values with the same indexes
if value1 != value2 // leave only different values in the list
} yield value2.toString
).toList
最好在zipped
使用zip
,而不是zipped
,因为List
不会在内存中生成整个压缩toList
。
此外,由于类型推断的怪癖,最后你必须using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Caching.Memory;
using System;
using Microsoft.Extensions.FileProviders;
namespace CachingQuestion
{
public class Startup
{
static string CACHE_KEY = "CacheKey";
public void ConfigureServices(IServiceCollection services)
{
//enabling the in memory cache
services.AddMemoryCache();
}
public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
var fileProvider = new PhysicalFileProvider(env.ContentRootPath);
app.Run(async context =>
{
//getting the cache object here
var cache = context.RequestServices.GetService<IMemoryCache>();
var greeting = cache.Get(CACHE_KEY) as string;
});
}
}
public class Program
{
public static void Main(string[] args)
{
var host = new WebHostBuilder()
.UseKestrel()
.UseStartup<Startup>()
.Build();
host.Run();
}
}
}
。
答案 1 :(得分:0)
这样的结果会产生相同的结果
val diff = for {
firstInner <- first
v1 <- firstInner
secondInner <- second
v2 <- secondInner
} yield if (v1 != v2) s"$v2}"
println(diff2 mkString ", ") // prints 23, 45
但如果数组大小不同,那么这个过程会因IndexOutOfBoundsException而失败。