DynamicObject 類別
定義
重要
部分資訊涉及發行前產品,在發行之前可能會有大幅修改。 Microsoft 對此處提供的資訊,不做任何明確或隱含的瑕疵擔保。
提供基底類別,以便指定在執行階段時的動態行為。 這個類別必須是繼承類別,您無法直接將其執行個體化。
public ref class DynamicObject : System::Dynamic::IDynamicMetaObjectProvider
public class DynamicObject : System.Dynamic.IDynamicMetaObjectProvider
[System.Serializable]
public class DynamicObject : System.Dynamic.IDynamicMetaObjectProvider
type DynamicObject = class
interface IDynamicMetaObjectProvider
[<System.Serializable>]
type DynamicObject = class
interface IDynamicMetaObjectProvider
Public Class DynamicObject
Implements IDynamicMetaObjectProvider
- 繼承
-
DynamicObject
- 衍生
- 屬性
- 實作
範例
假設您想要提供替代語法來存取字典中的值,因此,您可以撰寫 sampleDictionary.Text = "Sample text"
,而不是在 Visual Basic) 中撰寫 sampleDictionary["Text"] = "Sample text"
(sampleDictionary("Text") = "Sample text"
。 此外,您希望此語法不區分大小寫,因此相當於 sampleDictionary.Text
sampleDictionary.text
。
下列程式代碼範例示範 DynamicDictionary
衍生自 類別的 DynamicObject
類別。 類別DynamicDictionary
包含 Visual Basic 中類型 (Dictionary(Of String, Object)
的物件 Dictionary<string, object>
) 來儲存機碼/值組,並覆寫 TrySetMember 和 TryGetMember 方法來支援新的語法。 它也提供 Count
屬性,其中顯示字典包含多少個動態屬性。
// The class derived from DynamicObject.
public class DynamicDictionary : DynamicObject
{
// The inner dictionary.
Dictionary<string, object> dictionary
= new Dictionary<string, object>();
// This property returns the number of elements
// in the inner dictionary.
public int Count
{
get
{
return dictionary.Count;
}
}
// If you try to get a value of a property
// not defined in the class, this method is called.
public override bool TryGetMember(
GetMemberBinder binder, out object result)
{
// Converting the property name to lowercase
// so that property names become case-insensitive.
string name = binder.Name.ToLower();
// If the property name is found in a dictionary,
// set the result parameter to the property value and return true.
// Otherwise, return false.
return dictionary.TryGetValue(name, out result);
}
// If you try to set a value of a property that is
// not defined in the class, this method is called.
public override bool TrySetMember(
SetMemberBinder binder, object value)
{
// Converting the property name to lowercase
// so that property names become case-insensitive.
dictionary[binder.Name.ToLower()] = value;
// You can always add a value to a dictionary,
// so this method always returns true.
return true;
}
}
class Program
{
static void Main(string[] args)
{
// Creating a dynamic dictionary.
dynamic person = new DynamicDictionary();
// Adding new dynamic properties.
// The TrySetMember method is called.
person.FirstName = "Ellen";
person.LastName = "Adams";
// Getting values of the dynamic properties.
// The TryGetMember method is called.
// Note that property names are case-insensitive.
Console.WriteLine(person.firstname + " " + person.lastname);
// Getting the value of the Count property.
// The TryGetMember is not called,
// because the property is defined in the class.
Console.WriteLine(
"Number of dynamic properties:" + person.Count);
// The following statement throws an exception at run time.
// There is no "address" property,
// so the TryGetMember method returns false and this causes a
// RuntimeBinderException.
// Console.WriteLine(person.address);
}
}
// This example has the following output:
// Ellen Adams
// Number of dynamic properties: 2
' The class derived from DynamicObject.
Public Class DynamicDictionary
Inherits DynamicObject
' The inner dictionary.
Dim dictionary As New Dictionary(Of String, Object)
' This property returns the number of elements
' in the inner dictionary.
ReadOnly Property Count As Integer
Get
Return dictionary.Count
End Get
End Property
' If you try to get a value of a property that is
' not defined in the class, this method is called.
Public Overrides Function TryGetMember(
ByVal binder As System.Dynamic.GetMemberBinder,
ByRef result As Object) As Boolean
' Converting the property name to lowercase
' so that property names become case-insensitive.
Dim name As String = binder.Name.ToLower()
' If the property name is found in a dictionary,
' set the result parameter to the property value and return true.
' Otherwise, return false.
Return dictionary.TryGetValue(name, result)
End Function
Public Overrides Function TrySetMember(
ByVal binder As System.Dynamic.SetMemberBinder,
ByVal value As Object) As Boolean
' Converting the property name to lowercase
' so that property names become case-insensitive.
dictionary(binder.Name.ToLower()) = value
' You can always add a value to a dictionary,
' so this method always returns true.
Return True
End Function
End Class
Sub Main()
' Creating a dynamic dictionary.
Dim person As Object = New DynamicDictionary()
' Adding new dynamic properties.
' The TrySetMember method is called.
person.FirstName = "Ellen"
person.LastName = "Adams"
' Getting values of the dynamic properties.
' The TryGetMember method is called.
' Note that property names are now case-insensitive,
' although they are case-sensitive in C#.
Console.WriteLine(person.firstname & " " & person.lastname)
' Getting the value of the Count property.
' The TryGetMember is not called,
' because the property is defined in the class.
Console.WriteLine("Number of dynamic properties:" & person.Count)
' The following statement throws an exception at run time.
' There is no "address" property,
' so the TryGetMember method returns false and this causes
' a MissingMemberException.
' Console.WriteLine(person.address)
End Sub
' This examples has the following output:
' Ellen Adams
' Number of dynamic properties: 2
如需更多範例,請參閱 C# 常見問題部落格上的 使用 DynamicObject 建立包裝 函式。
備註
類別 DynamicObject
可讓您定義哪些作業可以在動態物件上執行,以及如何執行這些作業。 例如,您可以定義當您嘗試取得或設定物件屬性、呼叫方法,或執行標準數學運算,例如加法和乘法時會發生什麼事。
如果您想要為連結庫建立更方便的通訊協議,這個類別會很有用。 例如,如果您的連結庫使用者必須使用類似 的 Scriptobj.SetProperty("Count", 1)
語法,您可以提供使用更簡單語法的功能,例如 scriptobj.Count = 1
。
您無法直接建立 類別的 DynamicObject
實例。 若要實作動態行為,您可能想要繼承自 DynamicObject
類別,並覆寫必要的方法。 例如,如果您只需要設定和取得屬性的作業,您可以只 TrySetMember 覆寫 和 TryGetMember 方法。
在 C# 中,若要為衍生自 DynamicObject
類別的類別實例啟用動態行為,您必須使用 dynamic
關鍵詞。 如需詳細資訊,請參閱使用動態類型。
在 Visual Basic 中,晚期綁定支援動態作業。 如需詳細資訊,請參閱 Visual Basic) (早期和晚期系結 。
下列程式代碼範例示範如何建立衍生自 DynamicObject
類別的類別實例。
public class SampleDynamicObject : DynamicObject {}
//...
dynamic sampleObject = new SampleDynamicObject ();
Public Class SampleDynamicObject
Inherits DynamicObject
'...
Dim sampleObject As Object = New SampleDynamicObject()
您也可以將自己的成員新增至衍生自 類別的 DynamicObject
類別。 如果您的類別定義屬性並覆寫 TrySetMember 方法,動態語言執行平臺 (DLR) 會先使用語言系結器來尋找類別中屬性的靜態定義。 如果沒有這類屬性,DLR 會呼叫 TrySetMember 方法。
類別 DynamicObject
會實作 DLR 介面 IDynamicMetaObjectProvider,可讓您在支援 DLR 互操作性模型的語言之間共用 類別的 DynamicObject
實例。 例如,您可以在 C# 中建立 類別的 DynamicObject
實例,然後將它傳遞至 IronPython 函式。 如需詳細資訊,請參閱 動態語言執行平臺概觀。
注意
如果您有簡單的案例,其中需要物件,該物件只能在運行時間新增和移除成員,但不需要定義特定作業且沒有靜態成員,請使用 ExpandoObject 類別。
如果您有更進階的案例,您需要定義動態對象參與互操作性通訊協定的方式,或需要管理 DLR 快速動態分派快取,請建立您自己的介面實作 IDynamicMetaObjectProvider 。
建構函式
DynamicObject() |
讓衍生型別得以初始化 DynamicObject 型別的新執行個體。 |
方法
Equals(Object) |
判斷指定的物件是否等於目前的物件。 (繼承來源 Object) |
GetDynamicMemberNames() |
傳回所有動態成員名稱的列舉型別。 |
GetHashCode() |
做為預設雜湊函式。 (繼承來源 Object) |
GetMetaObject(Expression) |
提供分派給動態虛擬方法的 DynamicMetaObject。 此物件可以封裝在另一個 DynamicMetaObject 內部,以提供個別動作的自訂行為。 這個方法支援語言實作者適用的動態語言執行階段基礎結構,但不建議直接在程式碼中使用。 |
GetType() |
取得目前執行個體的 Type。 (繼承來源 Object) |
MemberwiseClone() |
建立目前 Object 的淺層複製。 (繼承來源 Object) |
ToString() |
傳回代表目前物件的字串。 (繼承來源 Object) |
TryBinaryOperation(BinaryOperationBinder, Object, Object) |
提供二進位運算的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定加法和乘法這類運算的動態行為。 |
TryConvert(ConvertBinder, Object) |
提供型別轉換作業的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定物件型別轉換作業的動態行為。 |
TryCreateInstance(CreateInstanceBinder, Object[], Object) |
提供作業的實作,這些作業會初始化動態物件的新執行個體。 這個方法並不適用於 C# 或 Visual Basic。 |
TryDeleteIndex(DeleteIndexBinder, Object[]) |
提供依索引刪除物件之作業的實作。 這個方法並不適用於 C# 或 Visual Basic。 |
TryDeleteMember(DeleteMemberBinder) |
提供刪除物件成員之作業的實作。 這個方法並不適用於 C# 或 Visual Basic。 |
TryGetIndex(GetIndexBinder, Object[], Object) |
提供依索引取得值之作業的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定索引作業的動態行為。 |
TryGetMember(GetMemberBinder, Object) |
提供取得成員值之作業的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定取得屬性值這類作業的動態行為。 |
TryInvoke(InvokeBinder, Object[], Object) |
提供叫用物件之作業的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定叫用物件或委派這類作業的動態行為。 |
TryInvokeMember(InvokeMemberBinder, Object[], Object) |
提供叫用成員之作業的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定呼叫方法這類作業的動態行為。 |
TrySetIndex(SetIndexBinder, Object[], Object) |
提供依索引設定值之作業的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定依指定之索引存取物件之作業的動態行為。 |
TrySetMember(SetMemberBinder, Object) |
提供設定成員值之作業的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定設定屬性值這類作業的動態行為。 |
TryUnaryOperation(UnaryOperationBinder, Object) |
提供一元運算的實作。 衍生自 DynamicObject 類別的類別可以覆寫這個方法,以指定負號、遞增或遞減這類運算的動態行為。 |