c# - 在 C# 中,我可以包装 Func 来缓存结果吗

标签 c# func

我编写了返回 Func<int, long> 的代码计算整数序列。我想以最优雅的方式缓存中间结果。目前我的代码如下所示:

private static Func<int, long> A237585() {
    Func<int, long> A = null;
    Func<int, long> B = null;
    Func<int, long> C = null;
    A = CreateCachingFunc((n) => n == 0 ? 0 : B(n-1));
    B = CreateCachingFunc((n) => C(n) + (n == 1 ? 1 : 0));
    C = CreateCachingFunc(CreateSumProductPartitionSelect(A, (n, k) => Choose(n + k - 1, k)));
    return A;
}

private static Func<int, long> CreateCachingFunc(Func<int, long> original)
{
    var cache = new List<long>();
    Func<int, long> cachedVersion = (n) =>
    {
        while (n >= cache.Count) cache.Add(original(cache.Count));
        return cache[n];
    };
    return cachedVersion;
}

我希望它看起来像这样:

private static Func<int, long> A237585() {
    CachedFunc<long> A = null;
    CachedFunc<long> B = null;
    CachedFunc<long> C = null;
    A = (n) => n == 0 ? 0 : B(n-1);
    B = (n) => C(n) + (n == 1 ? 1 : 0);
    C = CreateSumProductPartitionSelect(A, (n, k) => Choose(n + k - 1, k));
    return A;
}

这可能吗?我将如何编写 CachedFunc 以在返回时将 CachedFunc 隐式转换回 Func,并将匿名 lambda 隐式转换(包装)为缓存版本?如果不可能,那么包装我的函数的最好看的方式是什么?我希望顶层代码看起来尽可能简单。

最佳答案

让我们首先将使用 lambda 的现有内存实现转换为显式捕获类(这与 C# 编译器在看到 lambda 时自动创建的类几乎相同):

class CachedFunc<T>
{
     private List<T> cache;
     private Func<int, T> original;
     private T Call(int n)
     {
        while (n >= cache.Count) cache.Add(original(cache.Count));
        return cache[n];
     }

     public static Func<int, long> Create(Func<int, T> original)
     {
         return new CachedFunc<T>() { cache = new List<T>(), original = original }.Call;
     }
}

现在,我们只需要添加隐式转换:

class CachedFunc<T>
{
     private List<T> cache;
     private Func<int, T> original;
     private T Call(int n) {
        while (n >= cache.Count) cache.Add(original(cache.Count));
        return cache[n];
     }

     public static implicit operator CachingFunc<T>(Func<int, T> original)
     {
         return new CachedFunc<T>() { cache = new List<T>(), original = original };
     }

     public static implicit operator Func<int, T>(CachingFunc<T> memo)
     {
         return memo.Call;
     }
}

关于c# - 在 C# 中,我可以包装 Func 来缓存结果吗,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21816817/

相关文章:

c# - Func<S, T> 的 T 仅在 S 和 T 不同时才从 lambda 表达式的输出中推断出来?

c# - 优化从表达式树生成的 Func.Invoke()

c# - 使用 C# 在 Visio 中创建状态图

c# - 用 C# 打开 .sqlite 文件

c# - 如何将 Dictionary<string,MyClass> 转换为 Dictionary<string,object>

c# - 在 linqQuery 中只返回部分字符串

c# - 如何通过 ConverterParameter 将 TimeSpan.FromSeconds 传递给转换器?

linq - 具有其他类型泛型 Func 参数的扩展方法

.net - 如何在 Spring.net 中注入(inject) Predicate 和 Func

c# - 在 .Net 中测试复杂的 T-SQL 脚本?