C#通过添加属性来扩展类

Van*_*s S 10 c# oop

在C#中是否可以扩展一个类,而不仅仅是添加函数而是属性.例如:我有一个我依赖的标准DLL库,供应商不想修改它.

在整个代码中我已经广泛使用了DataCell类,现在才意识到我需要为它添加一个额外的属性,因为创建一个继承自这个类的新扩展类看起来不会起作用+大量的重写.

DataCell [元数据]

public class DataCell : Message
{
public int Field1;
public int Field2;
public DataCell()
{
 ..
} 
..
}
Run Code Online (Sandbox Code Playgroud)

基本上我想添加一个public int Flags; 到这堂课.所以我现在可以做而不重写任何东西,(新的DataCell).Flags = 0x10;

dss*_*539 10

首先,您应该重新考虑您的方法.但是,如果一切都失败了,这里是你如何可以排序的属性添加到一个密封类:

using System;
using System.Runtime.CompilerServices;

namespace DataCellExtender
{

    #region sample 3rd party class
    public class DataCell
    {
        public int Field1;
        public int Field2;
    }
    #endregion

    public static class DataCellExtension
    {
        //ConditionalWeakTable is available in .NET 4.0+
        //if you use an older .NET, you have to create your own CWT implementation (good luck with that!)
        static readonly ConditionalWeakTable<DataCell, IntObject> Flags = new ConditionalWeakTable<DataCell, IntObject>();

        public static int GetFlags(this DataCell dataCell) { return Flags.GetOrCreateValue(dataCell).Value; }

        public static void SetFlags(this DataCell dataCell, int newFlags) { Flags.GetOrCreateValue(dataCell).Value = newFlags; }

        class IntObject
        {
            public int Value;
        }
    }


    class Program
    {
        static void Main(string[] args)
        {
            var dc = new DataCell();
            dc.SetFlags(42);
            var flags = dc.GetFlags();
            Console.WriteLine(flags);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

除非你真的必须,否则请不要这样做.如果有一个更清晰的解决方案,你跳过这个稍微有点hacky的方法,那么这段代码的未来维护者可能会有一些强有力的话.

  • 这绝对是一个有趣的解决方法。我会先探索更清洁的选择,但至少值得考虑。 (2认同)

Jon*_*eet 7

那么你当然可以扩展一个类,只添加字段/属性(虽然我不鼓励根据你的样本使用公共字段).但是,除非其他代码使用您的新类,否则这些字段将不会存在于创建的对象中.例如,如果其他代码具有:

DataCell cell = new DataCell();
Run Code Online (Sandbox Code Playgroud)

那么会不会有你Field1Field2领域.

如果基类的每个实例都应该具有这些字段,那么最好不要考虑如何更改基类而不是扩展它.

如果您想知道是否可以像添加扩展方法一样添加"扩展字段" (例如public static void Foo(this DataCell cell)),那么不,那是不可能的.


小智 5

有两种方法可以向现有类添加属性

  1. 添加分部类,但这对您不起作用,因为分部类应该在同一个程序集中。

  2. 在不同的类中继承这个类,据我所知,这对你来说是一个更好的解决方案。

不,您不能像扩展方法一样使用扩展属性。