Чи можна застосувати методи розширення до інтерфейсів?


123

Чи можна застосувати метод розширення до інтерфейсу? (C # питання)

Наприклад, для досягнення наступного:

  1. створити інтерфейс ITopology

  2. створити метод розширення для цього інтерфейсу (наприклад, загальнодоступний статичний int CountNodes (ця топологія ITopologyIf))

  3. то при створенні класу (наприклад, MyGraph), який реалізує ITopology, тоді він автоматично матиме розширення Count Nodes.

Таким чином, класи, що реалізують інтерфейс, не повинні мати встановлене ім'я класу, щоб вирівняти те, що було визначено методом розширення.

Відповіді:


188

Звичайно, вони можуть; більшість Linq побудована на основі методів розширення інтерфейсу.

Інтерфейси насправді були однією з рушійних сил для розробки методів розширення; оскільки вони не можуть реалізувати будь-яку власну функціональність, методи розширення є найпростішим способом асоціювання фактичного коду з визначеннями інтерфейсу.

Дивіться клас Enumerable для всієї колекції методів розширення, побудованих навколо IEnumerable<T>. Реалізувати його - це те саме, що реалізувати для класу:

public static class TopologyExtensions
{
    public static void CountNodes(this ITopology topology)
    {
        // ...
    }
}

Що стосується інтерфейсів, то щодо методів розширення немає нічого особливого; метод розширення - це лише статичний метод, до якого компілятор застосовує деякий синтаксичний цукор, щоб він виглядав так, що метод є частиною цільового типу.


33
Re: "Звичайно" - я думаю, що питання розкриває запах архітектури, який ви неявно згадуєте. Якщо у вас можуть бути розширення на інтерфейсах, чому інтерфейси не можуть містити реалізовані методи? Зрозуміло, що думати, що будь-який інтерфейс повинен мати конкретні методи, або, коли ви знаєте, що вони не можуть, думати, що методи розширення не повинні допускатись як життєздатне шахрайство. (Але вони є. Не аргументуючи свою чудову відповідь, просто "звичайно" і посилання на IEnum, а не LINQ .; D) Щось тут смердючі!
рюш

Хочеться додати новини до коментаря @ruffin, що тепер ви можете додавати реалізації за замовчуванням до методів інтерфейсу C #. Джерело: devblogs.microsoft.com/dotnet/…
Vinigas

@ruffin Я вважав це найбільш заплутаним архітектурним рішенням у C #. Іноді це закінчується напівкласовою структурою напівінтерфейсу, що псує все навколо. Тим не менш, я вважаю, що це може бути корисно, коли підходити з точки зору функціонального програмування та використовуватись для впровадження утиліт до інтерфейсів, а не для реалізації функціональних можливостей.
Guney Ozsan
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.