2010-11-15 97 views
17

這不能在C#中完成。任何方式來做到這一點?將「NonSerializedAttribute」設置爲自動屬性

...

,萬一我的小雙關語不明白,我的意思是:我怎麼可以標記在C#中的財產作爲非序列化?當然,當屬性包含邏輯時,很自然無法做到這一點,但自動屬性是可序列化的,因此,我希望有一些方法可以讓我阻止它們的序列化。

+3

這是不可能的。 – SLaks 2011-01-02 00:20:34

回答

5

編輯*: 自動實現的屬性是由一個匿名的土地,你真的沒有獲得支持,屬性的目的是通過反射機制基礎來控制。這些字段不能被反射機制引用(因爲它們是匿名的)。此編譯器功能需要對自動屬性生成進行大量更改......它還需要編譯器將自動屬性作爲字段來處理,以便將字段屬性標記到其上。

要回答這個問題的更基本的部分 - 你的觀點是自動屬性是序列化的,所以應該有一種方法來控制它們的序列化。你是對的 - 但汽車屬性是一種速記,從來沒有設計爲給你充分的靈活性,而是讓你可以在需要的時候輕鬆擴展功能。

  • 我在答案的正文中添加了更多來自我的評論的答案。
+0

我不是C#noob :: - )。我知道這些事情。即便如此,編譯器可以添加一個特殊的自動屬性檢查並允許NonSerialized屬性。如果他們被序列化,他們應該被標記爲忽​​略。我知道我可以做到這一點,如果我創建setter/getters,但這是另一個故事,並且與我的問題無關:: - )。 – Axonn 2011-04-06 00:02:00

+1

:) 在這種情況下,我爲您提供了一個更好的解釋: 自動實現的屬性由匿名字段支持,您無法真正訪問它,屬性被設計爲由基於反射的機制控制。這些字段不能被反射機制引用(因爲它們是匿名的)。 您的編譯器功能需要對自動屬性生成進行大量更改... 它還需要編譯器將auto-properties作爲字段來處理,以便將字段屬性標記到字段屬性上。 – NightDweller 2011-04-06 21:06:40

+0

我注意到,這仍然不能回答你的問題的根本部分 - 你的觀點是自動屬性是序列化的,所以應該有一種方法來控制它們的序列化。 你是對的 - 但汽車性能是一種速記,從來沒有被設計爲給你充分的靈活性,而是讓你可以在需要的時候輕鬆地延長其功能。 – NightDweller 2011-04-06 21:16:53

-4

[NonSerialized] public decimal yourproperty;

(十進制爲例。)

還要記住,如果你想使你的類自動初始化非序列化成員,使用IDeserializationCallback接口,然後實現IDeserializationCallback.OnDeserialization。

+5

他說**財產**。這是一個領域。 – SLaks 2010-11-15 13:24:53

+0

o,是的。我錯過了。 – 2010-11-15 13:29:54

1

我的理論是的,這是可能的。在實際中,不可能。

序列化類只適用於專用字段。當你定義一個自動屬性時;在後臺編譯器會自動爲它生成一個專用字段。這意味着這是一種語言功能,而不是.net框架功能。

還有序列化類包含在redbits中,這是任何更改被禁止的兼容性,除了錯誤修復。

我希望這有幫助。

7
[NonSerialized] 
    public string MyProperty { get; set; } 

是錯誤的

[XmlIgnore] 
    public string MyProperty { get; set; } 

是不是一個錯誤

非序列化指示可序列化類的某個字段不應被序列化。

XmlIgnore指示的XmlSerializer的Serialize方法不序列化公共字段或公共讀/寫屬性值

所以,如果你問

我希望有一些讓我阻止他們的序列化的方式。

的回答是,如果你使用的XmlSerializer

+0

將'XmlIgnoreAttribute'應用到屬性導致該屬性不再出現在生成的XML文檔中。 – 2015-10-12 20:13:10

1

什麼上面說的是對的:你不能阻止一個自動實現的屬性通過設置如[非序列化]屬性正在連載。它只是不起作用。

但是,如果您使用WCF [DataContract],那麼工作是[IgnoreDataMember]屬性是什麼。因此,

[DataContract] 
public class MyClass 
{ 
    [DataMember] 
    public string ID { get; set; } 

    [IgnoreDataMember] 
    public string MySecret { get; set; } 
} 

將WCF序列化。

儘管由於WCF是一種選擇加入技術,您也可以忽略[IgnoreDataMember]並且它也可以工作。因此,也許我的評論是一個小學院;-)

0

你可以用Mono.Cecil,一個字節碼操作庫做到這一點。理論上,您可以將自定義屬性添加到隱藏的支持字段。然而,這很不方便,我認爲這不是一個例子。

如果你有一個自己的後處理器的大型應用程序,你可以考慮創建自己的替代NonSerializedAttribute,可以應用於屬性。然後後處理器可以使用Mono.Cecil或類似的方法將NonSerializedAttribute應用於後臺字段。大型應用程序經常進行這樣的後處理以節省多餘的打字量是很常見的。

3

對於事件,您可以使用[field:NonSerialized],但對於自動屬性,這不起作用。看起來這也是處理自動屬性的一種非常合乎邏輯的方式,但由於某種原因,它似乎並未實現。