2013-07-24 2 views
3

Я хочу создать интерфейс с помощью метода GetId(). В зависимости от подэлементов это может быть либо int, string, либо что-то еще. Вот почему я попробовал объект возвращаемого типа (но тогда я не могу указать тип в подэлементах) и хотел попробовать с помощью дженериков.Создать общее свойство в интерфейсе

Как я могу это сделать?

Что у меня уже есть:

public interface INode : IEquatable<INode> 
{ 
    object GetId(); 
} 

public class PersonNode : INode 
{ 
    object GetId(); //can be int, string or something else 
} 

public class WorkItemNode : INode 
{ 
    int GetId(); //is always int 
} 

Спасибо!

+1

Вы посмотрели на какие-либо из ссылок «Соответствующие», размещенные справа от этой страницы .. ?? – MethodMan

+0

Пожалуйста, объясните, как идентификатор PersonNode может быть int, string или somethign else. – Maarten

+0

@ DJKRAZE Да. Но это не показало мне решение, которое я получил от Jeppe Stig Nielsen. – casaout

ответ

3

Либо изменить INode интерфейс общего типа interface INode<out T> как предложено другие ответы.

Или, если вы не хотите, что реализовать без универсального интерфейса в явном виде и предоставить открытый метод типобезопасный, а также:

public class WorkItemNode : INode 
{ 
    public int GetId() //is always int 
    { 
     ... 
     // return the int 
    } 

    object INode.GetId() //explicit implementation 
    { 
     return GetId(); 
    } 

    ... 
} 
+0

Второй способ. Большое спасибо за этот отличный намек! – casaout

4

Это должно сделать:

public interface INode<T> : IEquatable<INode<T>> 
{ 
    T GetId(); 
} 

BTW: GetId() является метод.

Свойство будет выглядеть следующим образом:

public interface INode<T> : IEquatable<INode<T>> 
{ 
    T Id 
    { 
     get; 
     set; 
    } 
} 
+0

Большое спасибо! Ups, я непреднамеренно написал свойство, но закодировал метод;) – casaout

+1

И, конечно же, можно использовать свойство с помощью только 'get' accessor, не' set'. –

1

Может ваш интерфейс INode быть на самом деле INode<T> где Т INT, строка, что? Тогда ваше свойство может быть типом T.

Если вам нужно наследование, то у вас есть INode<T> и INode интерфейсов, где INode<T> имеет материал типоспецифического и INode имеет материал, не типоспецифический (и объект на основе свойства или метод для поиска Id)

6

Вы почти там, просто определить свой интерфейс, используя INode<T>

public interface INode<T> : IEquatable<INode<T>> 
{ 
    T GetId(); 
} 

public class PersonNode : INode<string> 
{ 
    public bool Equals(INode<string> other) 
    { 
     throw new NotImplementedException(); 
    } 

    public string GetId() 
    { 
     throw new NotImplementedException(); 
    } 
} 

public class WorkItemNode : INode<int> 
{ 
    public int GetId() 
    { 
     throw new NotImplementedException(); 
    } 

    public bool Equals(INode<int> other) 
    { 
     throw new NotImplementedException(); 
    } 
} 

Вы можете даже использовать object с интерфейсом

public class OtherItemNode : INode<object> 
{ 
    public bool Equals(INode<object> other) 
    { 
     throw new NotImplementedException(); 
    } 

    public int Id { get; set; } 

    public object GetId() 
    { 
     return Id; 
    } 
} 
+0

Спасибо за ваш комментарий! – casaout

0

Он [РЗ решение для этого случая использования по умолчанию междунар тип, где вам нужно еще, использовать PersonNode T как общий тип, а WorkItemNode использовать int вместо T в качестве объявлений общего типа по умолчанию для классов

Смежные вопросы