2012-05-18 24 views
5

Mam do czynienia z wymogiem stworzenia statycznej metody na mojej klasie bazowej, ale nie podoba mi się, że muszę zadeklarować argumenty typu, więc zastanawiam się, czy mam zamiar o tym właściwą drogę.Lepszy sposób definiowania metody statycznej

Zasadniczo przydzielam delegatów, których kojarzę z właściwościami w klasie. Mógłbym łatwo umieścić metodę na odziedziczonych klas, tak jak poniżej:

public class Foo 
{ 
    public string Property1 { get; set; } 
} 

public class InheritsFoo : Foo 
{ 
    public void AssignDel<TVal>(
     Expression<Func<InheritsFoo, TVal>> expr, 
     Action<InheritsFoo, TVal> action) 
    { 
    } 
} 

Lub, w klasie przedłużacza, mogę to zrobić:

public static void AssignDel<T, TVal>(
    this T source, 
    Expression<T, TVal>> expression, 
    Action<T, TVal> action) 
    where T : Foo 
{ 
} 

Oba pozwoliłoby mnie do korzystania AssignDel w instancja klasy:

var foo = new InheritsFoo(); 
foo.AssignDel(x => x.Property1, handler); 

Ale mam wymaganie, aby AssignDel statyczne. To sprawia, że ​​sposób rozszerzenia jest bezużyteczny. Nadal działa w InheritsFoo, ale naprawdę chcę przenieść to do klasy bazowej. Gdy próbuję argument generyczne nie można wywnioskować, i muszę zmienić wykorzystanie metody:

InheritsFoo.AssignDel<InheritsFoo, string>(x => x.Property1, handler); 

czy istnieje sposób tu, innym sposobem w ten sposób, że nie myślę o?

EDYCJA: w celu rozwiązania problemu w komentarzach o tym, czy metoda rozszerzenia miałaby/powinna działać ... Poszedłem do adresu URL, do którego odwołuje się @Mark M. Okazuje się, że jeśli to napiszę ...

InheritsFoo foo = null; 
foo.AssignDel(x => x.Property1, handler); 

Który kompiluje (nie wiem, czy to będzie działać). Nadal nie sądzę, że kwalifikuje się to jako użycie metody statycznej, ponieważ "foo" jest nadal uważane za instancję; Instancja zerowa, ale mimo to instancja.

+3

Metody rozszerzeń są już statyczne. W jaki sposób wymóg, aby metoda stała się przeszkodą w stosowaniu metod rozszerzeń? –

+3

"Mam wymóg uczynienia" AssignDel' static ". Następnie uczyń go statycznym. –

+1

@Kirk: Chociaż metody rozszerzeń są zdefiniowane jako metody statyczne, mogą być używane tylko jako metody instancji klasy docelowej. –

Odpowiedz

0

udało mi się zrobić to, co potrzebne po prostu wdrażanie kolejny poziom w łańcuchu dziedziczenia.

public class Foo 
{  
    public string Property1 { get; set; } 
} 

public class Foo<T> : Foo 
{ 
    public static void AssignDel<TVal>(Expression<Func<T, TVal>> expr, Action<T, TVal> action) 
    { } 
} 

public class InheritsFoo : Foo<InheritsFoo> 
{  } 

Potrafię leczyć InheritsFoo dokładnie tak, jak tego potrzebuję.

1

Ale mam wymóg, aby AssignDel stał się statyczny. To sprawia, że ​​rozszerzenie tego sposobu jest bezużyteczne. Nadal działa w InheritsFoo, ale Naprawdę chcę przenieść to do klasy bazowej. Gdy próbuję, generyków argumentu nie można wywnioskować, i muszę zmienić wykorzystanie metody :

To nie ma wiele sensu.

InheritsFoo.AssignDel to metoda statyczna.

Wywołujesz wspomnianą metodę statyczną wykonując InheritsFoo.AssignDel<InheritsFoo, string>(x => x.Property1, handler);, która wydaje się spełniać twoje wymagania.

Nie rozumiem, co jest nie tak z drugą opcją, którą wymyśliłeś. Robi to, co musisz zrobić, jasne jest, co się dzieje, czy to naprawdę dlatego, że przekazujesz InheritsFoo i string zamiast foo.AssignDel(x => x.Property1, handler);?

Wygląda na to, że można po prostu wykonać następujące czynności i osiągnąć to, co chcesz.

public class Foo 
    { 
     public string Property1 { get; set; } 
    } 

    public class InheritsFoo : Foo 
    { 
     public static void AssignDel<TVal>(
      Expression<Func<InheritsFoo, TVal>> expr, 
      Action<InheritsFoo, TVal> action) 
     { 
     } 
    } 

I musi być brakuje czegoś, ponieważ wydaje się, że można go używać InheritsFoo.AssignDel(x => x.Property1, handler); który jest dokładnie to, co chcesz.

+0

Określanie argumentów generycznych działa, ale jest bardziej szczegółowe niż byłoby preferowane, szczególnie w przypadku argumentu typu TVal. Dlatego proszę o alternatywy. – Random

1

Metoda rozszerzenia jest już statyczna.

Przypuśćmy, trzeba, aby nie używać go w sposób metodę rozszerzenia, to powinno działać:

InheritsFoo.AssignDel(x => x.Property1, handler); 

W ten sam sposób kompilator infere parametry typu dla postaci metodę rozszerzenia, to będzie za stary -Studowany sposób statyczny.

Jeśli trzeba mieć metodę z dwóch parametrach, typu, można utworzyć rodzajowe klasy dla tego:

public class Foo<T> where T : Foo { 

    public void AssignDel<TVal>(Expression<Func<T, TVal>> expr, Action<T, TVal> action) 
    { 
     //... 
    } 
} 

w tym przypadku można zrobić:

Foo<InheritFoo>.AssignDel(x => x.PropertyFromInheritFoo, handler); 

jak można zobacz, musisz tylko zadeklarować jeden parametr typu, drugi jest skazany.

Nadzieja pomaga

+0

To zadziała, jeśli zachowam metodę w InheritsFoo, kiedy chcę przenieść ją do podstawowej klasy Foo. – Random

+0

Och! Mam problem, z którym stoisz. Wygląda na to, że jesteś śrubą :( – ivowiblo

+0

Więc ... pozwól mi sprawdzić, czy rozumiem: chcesz mieć metodę w klasie Foo i zaakceptować właściwości dla całej hierarchii? – ivowiblo

Powiązane problemy