Как я могу использовать расширение для добавления соответствия интерфейса типу, который находится вне моего контроля? - PullRequest
0 голосов
/ 16 января 2020

На расширениях на странице документации Beef говорится следующее:

Расширения могут быть полезны для добавления соответствия интерфейса типам, которые находятся за пределами ваш элемент управления (ie: системные типы или типы, определенные в другой библиотеке).

К сожалению, он не предоставляет пример этого варианта использования, и я не знаю, как действовать дальше.

Предположим, у меня есть интерфейс IFooBarable:

interface IFooBarable
{
    void FooBar();
} 

И я хотел бы добавить этот метод расширения к типу системной библиотеки System.DateTime:

namespace System
{
    extension DateTime
    {
        public void FooBar()
        {
            String s = scope .();
            ToLongTimeString(s);

            Console.WriteLine("This dateTime ({}) has FooBarred", s); 
        }
    }
}

... такой, что DateTime может реализовать IFooBarable.

Должен ли быть способ, которым можно сказать компилятору трактовать DateTime как реализацию IFooBarable? Например, такой, что это компилируется:

using System;

interface IFooBarable
{
    void FooBar();
}

/* extension code here */

namespace Program
{
    public class Program
    {
        static void Main()
        {
            IFooBarable t = DateTime.Now;

            t.FooBar();
        }
    }
}

1 Ответ

0 голосов
/ 16 января 2020

Оказывается, это так же просто, как использовать тот же синтаксис, который указывает на реализацию в объявлении класса. То есть все, что вам нужно сделать выше, это использовать extension DateTime : IFooBarable:

using System;

interface IFooBarable
{
    void FooBar();
}

namespace System
{
    extension DateTime : IFooBarable
    {
        public void FooBar()
        {
            String s = scope .();
            ToLongTimeString(s);

            Console.WriteLine("This dateTime ({}) has FooBarred", s); 
        }
    }
}

namespace Program
{
    public class Program
    {
        static void Main()
        {
            IFooBarable t = DateTime.Now;

            t.FooBar();
        }
    }
}

Вы можете даже сделать это, чтобы зарегистрировать метод, который класс уже имеет, как реализацию метода интерфейса того же самого имя, не имеющее ничего внутри extension:

using System;

interface IFooBarable
{
    void ToLongTimeString();
}

namespace System
{
    extension DateTime : IFooBarable
    {
    }
}

namespace Program
{
    public class Program
    {
        static void Main()
        {
            IFooBarable t = DateTime.Now;

            String s = scope .(); 
            t.ToLongTimeString(s);

            Console.WriteLine("{}", s);
        }
    }
}
...