我正在讀一些.NET 4+代碼,它在Lazy的構造函數中使用了一個lambda,就像這個new Lazy<Foo>(() => new Foo())
。當沒有參數傳遞給Foo
的構造函數時,它與new Lazy<Foo>()
有什麼不同?從新的懶惰<Foo>()到新的懶惰<Foo>(()=> new Foo())有什麼不同?
回答
如果你看看摘要問題的兩個構造...
// Summary:
// Provides support for lazy initialization.
//
// Type parameters:
// T:
// Specifies the type of object that is being lazily initialized.
public class Lazy<T> {
// Summary:
// Initializes a new instance of the System.Lazy<T> class. When lazy initialization
// occurs, the default constructor of the target type is used.
public Lazy();
//
// Summary:
// Initializes a new instance of the System.Lazy<T> class. When lazy initialization
// occurs, the specified initialization function is used.
//
// Parameters:
// valueFactory:
// The delegate that is invoked to produce the lazily initialized value when
// it is needed.
//
// Exceptions:
// System.ArgumentNullException:
// valueFactory is null.
public Lazy(Func<T> valueFactory);
}
這就是說,主要的區別是,你能做些什麼類型的第二個構造
如。 ...
new Lazy<Foo>(() => new Foo(){ SomeProperty = someValue});
new Lazy<Foo>(() => new Foo(someValue));
......這與默認的構造函數不同。
此外,如果該類型沒有默認構造函數而沒有參數,則new Lazy<T>()
可能會失敗。
從我的理解你會使用lambda表達式的形式,當你想傳遞參數在初始化中使用。我不認爲沒有參數的lambda有用例。
待NIT挑剔,反射創建對象的實例比執行更慢一個lambda來構造實例。當然,根據你的用例,它可能根本不重要,但某個地方的某個人可能會有一個用例。 –
我同意但是(有點)諷刺的是,不是5分鐘前我剛剛看到這個鏈接的另一個問題,你的評論讓我想起了它。 [Performance Rant](https://ericlippert.com/2012/12/17/performance-rant/) –
new Lazy<Foo>()
使用反射來創建一個Foo
的實例,使用類似下面的代碼Activator.CreateInstance(typeof(T))
來調用默認構造函數。這意味着Foo
必須具有默認構造函數。
另一方面,如果需要,Lazy<Foo>(Func<T>)
爲您構建通過Lazy類型創建的實例提供了更大的靈活性。
當類型可以使用默認構造函數實例化時,默認的Lazy構造函數很有用。這意味着new Lazy<Foo>(() => new Foo())
,其中Foo
不採用構造參數,在大多數情況下可簡化爲new Lazy<Foo>()
。
例外是當類型的構造函數是私有的 - 因爲如前所述默認的Lazy<T>
構造函數使用Activator.CreateInstance(typeof(T))
,如果構造函數是私有的,即使它沒有參數,這也不起作用。例如,如下一個可能實現使用Lazy<T>
單身:
public class Foo
{
// Notice that the Lazy(Func<T>) constructor is used here
// because Foo's constructor is private
private static readonly Lazy<Foo> _instance = new Lazy<Foo>(() => new Foo());
public static Foo Current => _instance.Value;
private Foo()
{
// Don't allow calling code to new
}
}
- 1. 爲什麼懶惰<T>不懶惰?
- 2. 封裝懶惰<T>
- 3. 不能隱含地將懶惰<Class>轉換爲懶惰<Interface>
- 4. 緩存屬性vs懶惰<T>
- 5. 手動設置懶惰值<T>
- 6. C#懶惰<T>&Race-to-initialize?
- 7. 懶惰的缺點<T>?
- 8. 懶惰評價不那麼懶惰?
- 9. 懶惰<T>與LazyThreadSafeMode.PublicationOnly和IDisposable
- 10. 懶惰<T> - 總是創建一個新的對象?
- 11. 如何調試懶惰<T>?
- 12. 懶惰<T>和LazyInit之間的區別<T>
- 13. 懶惰<T>如何解決需要new()約束?
- 14. 懶惰加載和懶惰評估有什麼區別?
- 15. MEF:懶惰<T>類型的反義詞是什麼?
- 16. 懶惰<T>重新初始化方法?
- 17. 懶惰的val做什麼?
- 18. 爲什麼懶惰<T>受限於靜態上下文?
- 19. F#懶惰評估與非懶惰
- 20. 是什麼讓一個符號變成懶惰或非懶惰?
- 21. 什麼是「懶惰緩存」?
- 22. Java正則表達式懶惰操作符不那麼懶惰?
- 23. Resharper Refactor字段的類型T到懶惰<T>
- 24. CompositDisposable不夠懶惰?
- 25. hGetContents太懶惰
- 26. 關於懶惰
- 27. SimpleInjector RegisterAll懶惰地
- 28. Swift中的懶惰
- 29. preg_match懶惰?
- 30. 懶惰SlidingDrawer
沒關係,這是一個愚蠢的問題的答案就在問題本身 – Jack