开发者

How can I make properties optionally Read-Only or settable in various related classes?

In my project, I am creating generic interfaces to be used by a number of classes. This includes some properties that must always be present.

Some of the classes will be generic, and therefore the property must be changeable at run-time. Some of the classes will be highly specialized, and therefore, the value of the prope开发者_StackOverflowrty will be hard-coded. I would like to be able to use Bindings in the user interface to display and, where possible, edit the values. Also, I can imagine that at some point, I would want to use reflection to determine if the properly is settable.

What is the best way to accomplish this?

1) Define the properties as read-write in the interface, but have an empty setter in the specialized classes. This appears to be a somewhat common practice, but I am concerned with how binding and reflection would work. A UI control would still appear editable, just that the change by a user would not take, right?

2) Define the properties as read-only in the interface, but provide a setter in the generic classes. I would expect that the UI, bound to use the interface, would still see the property as read-only, and not allow editing.

3) Define the properties as read-only in the interface, but provide some other function to change the value in generic classes. This clearly breaks the property paradigm, and a binding wouldn't know about it to allow editing.

Is there some other way to enable or disable the setters that would be recognized by bindings and reflection?


OK, here my 2 cents - you might not like what I am going to say.

If you have a property that is read-only sometimes and read-write other times and constant in the rest, you are having a leaky abstraction here were polymorphism probably will only result in confusion to the clients of your classes.

So either I would have 2 interfaces one with read-write the other read-only, or just abandon polymorphism for such properties.


You should definitely only have a getter on the properties in your interface. Having a setter that is not always implemented will only lead to confusion.

You can then implement a setter in the appropriate classes. Depending on your application, you might want to create an extended interface that allows for your property to be set.

Example:

    public interface ITest
    {
        int Test { get; }
    }

    public interface ITestExtended : ITest
    {
        new int Test { get; set; }
    }

    public class Monkey : ITestExtended
    {
        public int Test { get; set; }

        // Be carefull to explicitly implement the original interface
        int ITest.Test
        {
            get
            {
                return 7;
            }
        }
    }

    public class MonkeySimple : ITest
    {
        public int Test
        {
            get { return 10; }
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            ITestExtended monkey = new Monkey() { Test = 5 };
            ITest monkeySimple = monkey;

            Console.WriteLine(monkeySimple.Test);
            Console.WriteLine(monkey.Test);

            // Compiler error
            //monkeySimple.Test = 6;

            Console.ReadKey();
        }
    }
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜