W tym poście chciałbym wspomnieć o jednej pułapce, którą łatwo można przeoczyć.
Parametry opcjonalne pozwalają nam pominąć podanie wartości dla argumentu oznaczonego jako opcjonalny. Parametry nazwana łączą parametry metody z wartością za pomocą nazwy (w tradycyjnym modelu możemy przyjąć, że argumenty metody łączone są z wartościami kolejnością przesłanych parametrów).
class Program { static void Main(string[] args) { var customer = CreateCustomer(); //all parameters will be var customer1 = CreateCustomer("Patryk"); //assign only firstName, rest of parameters (optional) will be assigned with empty value var customer2 = CreateCustomer(email: "patryk.osowski@someemail.com"); //assign only email var customer3 = CreateCustomer(address: "Krakow, Wadowicka 4", firstName: "Sebastian", lastName: "Kowalski"); //assign address, firstName and lastName } public static Customer CreateCustomer(string firstName = "", string lastName = "", string address = "", string email = "") { return new Customer {FirstName = firstName, LastName = lastName, Address = address, Email = email}; } } public class Customer { public string FirstName { get; set; } public string LastName { get; set; } public string Address { get; set; } public string Email { get; set; } }
Powyżej przykład wywołania który zapewne każdy z was widział i pewnie stosuje.
Gdzie można stosować parametry nazwane i/lub opcjonalne? W metodach, indekserach, konstruktorach oraz delegatach.
Jakie wartości można przypisywać w deklaracji typu wartościowego? Dozwolone wartości:
- stałe wyrażenie, czyli wartość która może zostać wyliczona podczas kompilacji
- element typu wyliczeniowego
- wartość domyślna (string firstName = default)
Jeżeli zostanie użyte wyrażenie, które wymaga uruchomienia programu w celu jego obliczenie - kompilator zgłosi błąd podczas budowania projektu.
Parametry opcjonalne nie mogą mieszać się z parametrami wymaganymi. W deklaracji sygnatury metody muszą występować na końcu.
Można zadać pytanie - czy opcjonalne / nazwane parametry mają jakikolwiek wpływ na wydajność aplikacji? Nie mają. Kompilator podczas budowania kodu niejako "wrzuci" wartości w wywołanie metody. Z powyższego wynika jedna pułapka na, którą warto uważać. Najlepiej przedstawi to poniższy przykład:
Tworzymy dwa projekty - pierwszy to zwykła aplikacja konsolowa, druga to biblioteka z jedną klasą np. Sample jak w tym przypadku. Klasa Sample posiada jedną metodę z opcjonalnym parametrem:
using System; namespace OptionalParameterAssembly { public class Sample { public void PrintDefaultValue(int value = 5) { Console.WriteLine(value); } } }
Aplikacja konsolowa posiada referencję do biblioteki i wywołuje metodę PrintDefaultValue:
var sample = new Sample(); sample.PrintDefaultValue();
Po uruchomieniu aplikacji nie zobaczymy nic nadzwyczajnego - zostanie wyświetlona wartość 5:
Przejdźmy do sedna: Zmieńmy wartość domyślną w naszej bibliotece i skompilujmy tylko ją. Następnie skopiujmy ją do aplikacji konsolowej:
public void PrintDefaultValue(int value = 10) { Console.WriteLine(value); }
Jak myślicie co zostanie wyświetlone na ekranie po uruchomieniu OptionalNamedParameters.exe?
Dokładnie 5! Opcjonalne parametry łączone są z metodą w momencie kompilacji programu. Jeżeli więc używamy biblioteki i zawiera ona opcjonalne metody, należy zawsze pamiętać o skompilowaniu głównej aplikacji po zmianach w bibliotece.
Brak komentarzy:
Prześlij komentarz