Generic cached value class mimicking Lazy
First off, never lock on this. You never know who else is locking on that instance. Conversely, clients don't know that the cache is locking on itself either. For example, this seemingly innocent code would lead to a deadlock:

//Thread A
lock(cache)
lock(someObject)
{
    //do something
}

//Thread B
lock(someObject)
{
    //here, the cache will lock on itself.
    //the locks are accidentally taken in reverse order -&gt; deadlock!
    var x = cache.Value;
}


That's why it's good practice to lock on a private readonly object.
Moving on...

Your current implementation allows the value to be refreshed twice in a row. This is a problem if the resource is expensive to create (and resources worth caching usually are).

Two threads might check whether DateTime.Now &gt;= _expiration, then both go into the RefreshValue method and execute the critical region in quick sucession. To solve this you can either:


move the lock up to the place where the expiration date is being checked.
move the expiration check inside the RefreshValue method.


I would go with option 2, and add a double-checked lock to avoid hitting the lock every single time:

private readonly object _refreshLock = new object();

private void RefreshValueIfNeeded()
{
    if (DateTime.Now &gt;= _expiration)
    {
        lock (_refreshLock)
        {
            if (DateTime.Now &gt;= _expiration)
            {
                _value = new Lazy&lt;T&gt;(_valueFactory);
                _expiration = DateTime.Now.Add(_duration);
            }
        }
    }
}


public T Value
{
    get
    {
        RefreshValueIfNeeded();
        return _value.Value;
    }
}


One more thing: you don't need to wrap the value factory into another delegate, you can just pass it directly to Lazy&lt;T&gt;'s constructor:

//change this
new Lazy&lt;T&gt;(() =&gt; _valueFactory())
//to
new Lazy&lt;T&gt;(_valueFactory)