Интерфейс в C#

Я плохо знаком с ООП и имею некоторые вопросы.

  1. Почему не может, методы, объявленные в интерфейсе, имеют модификаторы (общедоступный, частный и т.д.).

  2. В этом коде:

class Program
{
    static void Main(string[] args)
    {
        X ob = new Y();
        ob.add(4, 5);
        Z ob1 = new Y();
        ob1.mull(2, 3);
        Console.Read();
    }
}

public interface X
{
    void add(int x, int y);
}
public interface Z
{
    void mull(int x, int y);
}

class Y : X, Z
{
    void X.add(int x, int y)//here we are not decalring it as public ,why?
    {
        Console.WriteLine("sum of X and y is " + (x + y));
    }
    void Z.mull(int x, int y)
    {
        Console.WriteLine("product of X and Y is" + (x * y));
    }
}

Оба метода не требуют модификаторов, но когда я не использую интерфейс, как X.add() выше, я должен обнародовать реализацию. Почему?

8
задан jason 30 January 2010 в 05:14
поделиться

8 ответов

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

public void add(int x, int y)
{
    Console.WriteLine("sum of X and y is " + (x + y));
}
public void mull(int x, int y)
{
    Console.WriteLine("product of X and Y is" + (x * y));
}

Это неявное внедрение интерфейса, и теперь легче назвать эти методы на экземпляре вашего класса. Просто позвоните MyInstance.add (1, 2) Вместо того, чтобы иметь значение myInstance , чтобы быть экземпляром интерфейса x .

-121--3434607-

Это разница между Осведомлением и Имея внедрение интерфейса.

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

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

0
ответ дан 5 December 2019 в 04:49
поделиться

Прямо из Microsoft: "Члены интерфейса всегда публичны, потому что назначение интерфейса - позволить другим типам получить доступ к классу или структуре"

.
1
ответ дан 5 December 2019 в 04:49
поделиться

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

Вы можете захотеть взглянуть на эти вопросы:

Как я узнаю, когда создавать интерфейс?
Почему я не могу иметь защищенных членов интерфейса?

2
ответ дан 5 December 2019 в 04:49
поделиться

Automod - это путь. http://www.appliedmaterials.com/products/automod_2.html

Есть чему поучиться, и это будет недешево.

Компания ASI Automod уже около 30 лет занимается моделированием производства. Теперь он принадлежит компании Applied Materials. Крупные игроки, которые работают с обработкой материалов на складе, используют Automod, потому что это проверенный лидер.

-121--3003493-

Я использую EmacsW32. C-h оболочка $ дает список команд запуска оболочки и команды cmd-shell и cygwin-shell выглядят интересно. Обе команды нуждаются в EmacsW32. Они также находятся в меню Tools > W & 32 Shells .

Если вы запускаете cygwin-shell впервые и не настроили путь cygwin в Emacs, это приведет вас к странице настройки, где вы можете настроить путь cygwin, нажав кнопку Найти.

-121--1227592-

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

0
ответ дан 5 December 2019 в 04:49
поделиться

Я использую Vim . Я нахожу его самым простым и чистым.

-121--3525891-

Вероятно, это также измерение общей памяти

-121--5086250-

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

public void add(int x, int y)
{
    Console.WriteLine("sum of X and y is " + (x + y));
}
public void mull(int x, int y)
{
    Console.WriteLine("product of X and Y is" + (x * y));
}

Это неявная реализация интерфейса, и теперь проще вызывать эти методы на экземпляре вашего класса. Просто вызовите myInstance.add (1, 2) вместо того, чтобы приводить myInstance в качестве экземпляра интерфейса X .

1
ответ дан 5 December 2019 в 04:49
поделиться

Я собираюсь вернуться и объяснить симптомы, которые вы сообщаете, а не стараетесь объяснить, почему публичный модификатор не нужен; Другие ответы объяснили это адекватно.

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

Если вы удалите «X.» Из вашей реализации X.ADD вы сможете «увидеть» и использовать интерфейс без явного отряда. Это «неявный» реализация интерфейса. До тех пор, пока у вас нет коллизий имен или некоторых причин сделать члены интерфейса чуть менее заметными для нормальных клиентов, вы, вероятно, хотите предпочитать неявный интерфейс реализации.

1
ответ дан 5 December 2019 в 04:49
поделиться

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

1
ответ дан 5 December 2019 в 04:49
поделиться

Интерфейс - это контракт. Он говорит: «Я могу это делать». Какой смысл передавать вам экземпляр IInterface , в котором вы не можете использовать некоторые методы в этом контракте, потому что они помечены как закрытые?

Это основание для разработки языка этим способом. Спецификация для этого находится в §13.2 спецификации языка:

Все элементы интерфейса неявно имеют открытый доступ. Когда объявления членов интерфейса включают какие-либо модификаторы, возникает ошибка времени компиляции. В частности, элементы интерфейсов не могут быть объявлены с модификаторами abstract , public , protected , internal , private, виртуальный , переопределить или статический .

Что касается вашего кода, это пример явной реализации интерфейса . Это наиболее полезно, когда класс или структура реализует два интерфейса, каждый из которых имеет член, имеющий одинаковую подпись. Например, и IEnumerable , и IEnumerable определяют метод GetEnumerator , не принимающий параметров.

public interface IEnumerable {
    IEnumerator GetEnumerator();
}

public interface IEnumerable<T> : IEnumerable {
    IEnumerator<T> GetEnumerator();
}

Обратите внимание, что согласно приведенным выше определениям любой класс, реализующий IEnumerable , также должен реализовывать IEnumerable . Имейте в виду, что тип возвращаемого значения не является частью подписи, и поэтому у нас есть конфликт с IEnumerable.GetEnumerator и IEnumerable .GetEnumerator .Вот для чего предназначена явная реализация интерфейса:

class X<T> : IEnumerable<T> {
    List<T> _list = new List<T>();
    public IEnumerator<T> GetEnumerator() {
        return _list.GetEnumerator();
    }

    IEnumerator GetEnumerator() {
        return GetEnumerator(); // invokes IEnumerable<T>.GetEnumerator
    }
}

Члены, которые являются явными реализациями интерфейса, видны только через экземпляр интерфейса. Таким образом:

X<int> x = new X<int>();
var e1 = x.GetEnumerator(); // invokes IEnumerable<int>.GetEnumerator
                           // IEnumerable.GetEnumerator is not visible
IEnumerable y = x;
var e2 = y.GetEnumerator(); // invokes IEnumerable.GetEnumerator

Таким образом, в вашем коде

X ob = new Y();
ob.add(1, 2); // X.add is visible through interface
Y y = new Y();
y.add(1, 2); // compile-time error, X.add is not visible

Оба метода не требуют модификаторов, но когда я не использую интерфейс, например X.add () выше, мне нужно сделать реализацию общедоступной. Почему?

Ладно, не совсем понятно, о чем вы здесь спрашиваете. Модификаторы доступа не допускаются для явных реализаций интерфейса. Это 13,4:

Это ошибка времени компиляции для явной реализации члена интерфейса, чтобы включить модификаторы доступа, и ошибка времени компиляции, чтобы включить модификаторы abstract , virtual , переопределить или статический .

Если реализация интерфейса не помечена как явная реализация интерфейса, тогда она должна иметь модификатор доступа public . Это 13.4.4 (Отображение интерфейса):

Отображение интерфейса для класса или структуры C определяет местонахождение реализации для каждого члена каждого интерфейса, указанного в списке базовых классов C . Реализация конкретного члена интерфейса I.M , где I - интерфейс, в котором объявлен член M , определяется путем изучения каждого класса или структуры S , начиная с ] C и повторяется для каждого последующего базового класса C , пока не будет найдено совпадение

  • Если S содержит объявление явной реализации члена интерфейса, которое соответствует ] I и M , тогда этот элемент является реализацией IM

  • В противном случае, если S содержит объявление нестатического открытого члена, который соответствует M , тогда этот элемент является реализацией IM .

Ошибка времени компиляции возникает, если реализации не могут быть найдены для всех элементов всех интерфейсов, указанных в списке базовых классов C .

Короче говоря, компилятор сначала ищет явную реализацию интерфейса. Если он не может найти его, он ищет нестатический, общедоступный член с той же сигнатурой, что и реализуемый метод M . Если он не может найти его, возникает ошибка времени компиляции. Итак, правила такие. Чтобы реализовать член интерфейса IM :

  1. Если вы реализуете IM явно, то синтаксис будет

    IM типа возврата (список параметров)

  2. В противном случае синтаксис является

    общедоступным возвращаемым типом M (список-параметров)

Таким образом, с

interface IAdd {
    int Add(int x, int y)
}

Мы можем реализовать явно:

class Explicit : IAdd {
    int IAdd.Add(int x, int y) { return x + y; }
}

или нет:

class NotExplicit : IAdd {
    public int Add(int x, int y) { return x + y; }
}

Разница в том, что Явный.Добавление не отображается, если экземпляры Explicit не набраны как IAdd :

IAdd explicitInterface = new Explicit();
explicitInterface.Add(2, 2);
Explicit explicit = new Explicit();
explicit.Add(2, 2); // compile-time error

, тогда как

IAdd notExplicitInterface = new NotExplicit();
notExplicitInterface.Add(2, 2);
NotExplicit notExplicit = new NotExplicit();
notExplicit.Add(2, 2); // okay, NOT a compile-time error as above

Это помогает?

34
ответ дан 5 December 2019 в 04:49
поделиться
Другие вопросы по тегам:

Похожие вопросы: