C # Общий дизайн интерфейсов и производительность - PullRequest
0 голосов
/ 11 сентября 2018

У меня есть базовый вопрос относительно общих интерфейсов.

Дело 1:

public interface IDataProcesser
{
    TOut Process<Tin,TOut>(Tin input);
}

Случай 2:

public interface IDataProcesser<Tin,TOut>
{
    TOut Process(Tin input);
}

Приводит ли Случай 1 к Боксу / Разблокировке? Является ли он менее производительным по сравнению со вторым вариантом. Существуют ли какие-либо правила при разработке универсальных интерфейсов?

Спасибо, Ravi

1 Ответ

0 голосов
/ 11 сентября 2018

Первый метод * на 1001 * более производительный , чем второй (по крайней мере, один мой ноутбук - см. Код ниже). Тем не менее, это не очень важная часть здесь.

  1. Если универсальные типы TIn и TOut имеют некоторое семантическое значение для интерфейса или большинства методов интерфейса, то следует включить общее описание в интерфейсе.

  2. Если только один или несколько методов, определенных в интерфейсе, используют универсальные типы, то вместо методов должно использоваться общее описание.

Однако, как вы, в частности, спросили о том, какая производительность выше, я набрал небольшой код и протестировал его. К моему удивлению, первый метод был на самом деле более производительным.

Первый метод занял 3669 миллисекунд, а второй - 2715.

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Runtime.InteropServices.WindowsRuntime;
using System.Text;
using System.Threading.Tasks;

namespace Sandbox
{
    public interface IDataProcesser
    {
        TOut Process<TIn, TOut>(TIn input);
    }

    public interface IDataProcesser2<TIn, TOut>
    {
        TOut Process(TIn input);
    }


    class Class1 : IDataProcesser
    {
        public TOut Process<Tin, TOut>(Tin input)
        {
            return default(TOut);
        }
    }

    class Class2 : IDataProcesser2<int, long>
    {
        public long Process(int input)
        {
            return default(long);
        }
    }

    class Program
    {
        private static int _loopCount = 1000000000;

        static void Main(string[] args)
        {
            var warmupEquals = false;
            var equals1 = false;
            var equals2 = false;

            for (long i = 0; i < _loopCount; i++)
            {
                Class1 warmup = new Class1();
                var w1 = warmup.Process<int, long>(default(int)) == 0;
                warmupEquals = w1;
            }

            var sw = new Stopwatch();
            sw.Start();
            for (long i = 0; i < _loopCount; i++)
            {
                Class1 c1 = new Class1();
                var t1 = c1.Process<int, long>(default(int)) == 0;
                if (t1)
                {
                    equals1 = true;
                }
            }

            sw.Stop();
            Console.WriteLine("Method 1");
            Console.WriteLine(sw.ElapsedMilliseconds);

            sw.Restart();
            sw.Start();
            for (long i = 0; i < _loopCount; i++)
            {
                Class2 c2 = new Class2();
                var t2 = c2.Process(default(int)) == 0;
                if (t2)
                {
                    equals2 = true;
                }
            }

            sw.Stop();
            Console.WriteLine("Method 2");
            Console.WriteLine(sw.ElapsedMilliseconds);
            Console.WriteLine(warmupEquals);
            Console.WriteLine(equals1);
            Console.WriteLine(equals2);
            Console.ReadLine();
        }
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...