Метод Перегрузка с другим типом возврата

Я хочу понять, что это двусмысленность или дополнительная функция, которая предоставляется:

 public class Foo 
 { 
    public int Bar(){
       //code
    }

    public string Bar(int a){
       //code
    }
 }

Любой, имеющий какой-либо опыт с этим, перегрузка по типу возврата с разными параметрами должна быть плохой практикой, не так ли?

Но если перегрузка была выполнена на основе типа возврата, то почему это не работает.

 public class Foo 
 { 
    public int Bar(int a){
       //code
    }

    public string Bar(int a){
       //code
    }
 }

Поскольку он не сможет решить, какую функцию вызывать 1 или 2, если мы назовем obj.Bar();, это должно закончиться ошибкой, если у кого-нибудь есть представление об этом, почему он позволяет запускать первый фрагмент кода.

Ответ 1

В спецификации С# (раздел 10.6) указано, что перегруженные члены могут не отличаться только типом возвращаемого значения и http://msdn.microsoft.com/en-us/library/ms229029.aspx

В соответствии с вашим вопросом относительно создания параметров просто поддерживать разные типы возвращаемых данных? Я лично считаю, что это ужасное решение проблемы. Обслуживание кода станет трудным, а неиспользуемые параметры - это определенный запах кода. Действительно ли этот метод необходимо перегружать в этом случае? Или он принадлежит к этому классу? Должно ли создаваться что-то еще для преобразования из одного типа возврата в другой? Все, что вы должны попросить вывести более идиоматическое решение.

Ответ 2

Это логически невозможно. Рассмотрим следующий вызов:

object o = Bar(42);

или даже

var o = Bar(42);

Как компилятор узнает, какой метод вызывать?

Изменить: Теперь, когда я понимаю, что вы на самом деле спрашиваете, я думаю, что перегрузка по бессмысленным параметрам - это плохая практика и уменьшенная читаемость, гораздо предпочтительнее различать по имени метода:

 string BarToStr()
 {

 }

 int BarToInt()
 {

 }

Ответ 3

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

  • Типы параметров
  • Количество параметров
  • Порядок параметров, объявленных в методе

Вы не можете узнать, какая функция фактически вызвана (если это было возможно).

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

Итак, это еще один способ понять, почему перегрузка метода невозможна только с помощью типа возврата.

Ответ 4

Другие уже объяснили ситуацию. Я только хотел бы добавить это: вы можете делать то, что имеете в виду, используя параметр типового типа:

public T Bar<T>(int a) {
   // code
}

И назовите его следующим образом:

int i = Bar<int>(42);
string s = Bar<string>(42);

Проблема заключается в том, что часто бывает сложно сделать что-то значимое с общим типом, например. вы не можете применять к нему арифметические операции. Иногда общие ограничения типов могут помочь.

Ответ 5

любой, у кого есть опыт с этим, перегрузка по типу возврата с разными параметрами должно быть плохой практикой, не так ли.

Я беру это в виду - "это плохая практика использовать разные комбинации параметров для облегчения разных типов возврата" - если это действительно вопрос, то просто представьте себе, что кто-то другой через этот код через несколько месяцев - эффективно "dummy" для определения типа возврата... было бы довольно сложно понять, что происходит.

Изменить - как указывает ChrisLava, "путь вокруг этого состоит в том, чтобы иметь лучшие имена для каждой функции (вместо перегрузки). Имена, которые имеют ясное значение в приложении. Нет причин, по которым Bar должен возвращать int и строку. Я мог видеть, как просто вызывает ToString() в int"

Ответ 6

С# не позволяет его.

С#, с другой стороны, не поддерживает разрешение метода на основе тип возврата; это было сознательное решение разработчиков языка не раскрывать функцию CLR, которая позволяет это. Нет техническая причина, почему они не могли этого сделать, они просто чувствовали это лучше не. Поскольку возвращаемое значение не используется для выбора метода a Подпись метода С# не включает его.

Ответ 7

Вы не можете создать метод с тем же именем, с тем же числом и типами параметров.

Подробнее см. ссылку .

Ответ 9

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

Это будет работать (что означает "Скомпилировать" ), но все равно плохой дизайн.

public class Foo
{
    public object Bar(int a)
    {
        return a;
    }
}