2009-10-20 18 views
20

Jakie podejścia podejmują ludzie (jeśli występują) w zarządzaniu eksplozją na zajęciach w klasie guard clause? Na przykład:Refaktorowe klauzule strażnicze

public void SomeMethod<T>(string var1, IEnumerable<T> items, int count) 
{ 
    if (string.IsNullOrEmpty(var1)) 
    { 
     throw new ArgumentNullException("var1"); 
    } 

    if (items == null) 
    { 
     throw new ArgumentNullException("items"); 
    } 

    if (count < 1) 
    { 
     throw new ArgumentOutOfRangeException("count"); 
    } 

    ... etc .... 
} 

W projekcie, nad którym obecnie pracuję, istnieje wiele klas, które mają podobny zestaw klauzul ochronnych na publicznych metodach.

Jestem świadomy kontraktów kodu .NET 4.0, jednak obecnie nie jest to opcja dla naszego zespołu.

Odpowiedz

39

wiele projektów, które widziałem używać statycznego Guard klasę.

public static class Guard { 
    public static void ArgumentIsNotNull(object value, string argument) { 
     if (value == null) 
      throw new ArgumentNullException(argument); 
    } 
} 

To sprawia, że ​​kod jest dużo czystszy, moim zdaniem.

Guard.ArgumentIsNotNull(arg1, "arg1"); 
+1

Po prostu napisałem to samo. Jedyny problem polega na tym, że metoda ta znajduje się na początku śledzenia stosu w porównaniu do metody początkowej u góry, a nie, że jest tak ogromna. Ten wzorzec oczywiście może być użyty dla różnych typów, aby sprawdzić zakres wartości, itp. –

+0

Tak, to jedyny problem, jaki kiedykolwiek miałem z tym.Chociaż łatwo znaleźć oryginalną metodę wywołania. –

+1

Jest to w zasadzie to samo, co klasy imitujące umowy kodu. –

5

Jeśli nie chcą zejść z trasy Code Contracts, jeden sposób, aby go uprościć jest usunięcie szelki:

public void SomeMethod<T>(string var1, IEnumerable<T> items, int count) 
{ 
    if (string.IsNullOrEmpty(var1)) 
     throw new ArgumentNullException("var1"); 

    if (items == null) 
     throw new ArgumentNullException("items"); 

    if (count < 1) 
     throw new ArgumentOutOfRangeException("count"); 

    ... etc .... 
} 

Poza tym, istnieje kilka sposobów, które można symulować Code Contracts , jeśli sprzeciw jest, że .NET 4.0 nie jest jeszcze w prime time:

http://geekswithblogs.net/Podwysocki/archive/2008/01/22/118770.aspx

+0

Na litość boską, nie rób tego! Jeśli stwierdzenia bez nawiasów klamrowych są świetnym sposobem na sprawienie sobie problemów na drodze. – EricRRichards

+1

@EricRRichards: * [wzrusza ramionami] * Szczerze mówiąc, jeśli programiści nie mogą zachować kodu bez nawiasów klamrowych (szczególnie nietypowy kod jak ten), prawdopodobnie powinni wrócić do szkoły. –

3

Jednym ze sposobów ograniczenia (nie całkowite usunięcie) Numer klauzul strażniczych jest zrozumienie przyczyny ich istnienia. Dość często okazuje się, że chronimy przed wartościami, które są ważne dla typu argumentu, ale nie są prawidłowe dla metody, która je akceptuje. Innymi słowy, metoda jest zdefiniowana w podzbiorze domeny zdefiniowanej przez typ argumentu.

Rozwiązaniem tej kategorii przypadków jest próba zdefiniowania podtypu (np. Bardziej restrykcyjnego interfejsu) i zaakceptowanie tego typu jako argumentu. Przykład ilustrujący ten artykuł: Why do We Need Guard Clauses?

Oczywiście ta technika nie dotyczy wszystkich przypadków. Wszystkie typy referencyjne przynajmniej pozwalają na zerowe odniesienia. W związku z tym większość naszych metod zostanie określona w części domeny, co z kolei wymaga klauzuli wartownika przeciwko zeru.

Jednak z pozytywnej strony technika ta pomaga zwiększyć świadomość na temat metod otrzymujących bardziej ogólne argumenty niż pożądane. Hydraulika tej dziury pomaga ogólnie poprawić projektowanie.