public static Func <CancellationToken, TParam, Task <TResult> > AsMemoized <TParam, TResult>(this Func <CancellationToken, TParam, Task <TResult> > func)
        {
            var values = new SynchronizedDictionary <TParam, Func <CancellationToken, Task <TResult> > >();
            // It's safe to use default(TParam) as this won't get called anyway if TParam is a vlue type.
            var nullValue = Funcs.CreateAsyncMemoized(ct => func(ct, default(TParam)));

            return((ct, param) =>
            {
                if (param == null)
                {
                    return nullValue(ct);
                }
                else
                {
                    var memoizedFunc = values.FindOrCreate(param, () => Funcs.CreateMemoized(c => func(c, param)));

                    return memoizedFunc(ct);
                }
            });
        }