«Программа для интерфейса» с использованием методов расширения :Когда это заходит слишком далеко?

Фон:В духе «программы для интерфейса, а не реализации» и классов типов Haskell и в качестве эксперимента по кодированию я думаю о том, что будет означать создание API, который в основном основан на сочетании интерфейсов и методов расширения. Я имею в виду два правила:

  1. По возможности избегайте наследования классов. Интерфейсы должны быть реализованы как sealed classes.
    (Это происходит по двум причинам :. Во-первых, потому что подклассы поднимают некоторые неприятные вопросы о том, как специфицировать и применять контракт базового класса в его производных классах. Во-вторых, и это влияние класса типов Haskell, полиморфизм не требует создания подклассов.)

  2. По возможности избегайте методов экземпляра. Если это можно сделать с помощью методов расширения, они предпочтительнее.
    ( Это сделано для того, чтобы интерфейсы оставались компактными. :Все, что можно сделать с помощью комбинации других методов экземпляра, становится методом расширения. Что остается в интерфейсе, так это основная функциональность и, в частности, методы изменения состояния -.)

Проблема:У меня проблемы со вторым правилом. Рассмотрим это:

interface IApple { }
static void Eat(this IApple apple)
{
    Console.WriteLine("Yummy, that was good!");
}

interface IRottenApple : IApple { }
static void Eat(this IRottenApple apple)
{
    Console.WriteLine("Eat it yourself, you disgusting human, you!");
}

sealed class RottenApple : IRottenApple { }
IApple apple = new RottenApple();
// API user might expect virtual dispatch to happen (as usual) when 'Eat' is called:
apple.Eat(); // ==> "Yummy, that was good!"

Очевидно, для ожидаемого результата("Eat it yourself…"), Eatдолжен быть обычным методом экземпляра.

Вопрос:Каким будет уточненное/более точное руководство по использованию методов расширения по сравнению с (методами виртуального )экземпляра? Когда использование методов расширения для «программирования интерфейса» заходит слишком далеко? В каких случаях на самом деле требуются методы экземпляра?

Я не знаю, существует ли какое-либо четкое общее правило, поэтому я не ожидаю идеального универсального ответа. Приветствуются любые хорошо аргументированные -улучшения руководства (2 )выше.

7
задан stakx supports GoFundMonica 11 July 2012 в 23:29
поделиться