2009-04-10 11 views
14

Inne osoby, które są w stanie sprawdzić wartości kontrolne w seterze, jest bardziej podstawowym powodem do preferowania właściwości do zmiennych publicznych?Dlaczego preferować właściwości dla zmiennych publicznych?

+0

Skutecznie dupe http://stackoverflow.com/questions/641619/when-should-you-using-a-field-rather-than-a-property i http://stackoverflow.com/questions/379041/what-is-the-best-practice-do-używania-public-fields/379057 - między innymi. – tvanfosson

Odpowiedz

22

Przedtem mieliśmy ten temat, ale nie mogę teraz znaleźć niczego.

W skrócie: Twoje potrzeby mogą się zmienić: w przypadku braku kontroli poprawności teraz, może być wymagane w przyszłości. Jeśli jednak zmienisz swoje publiczne pola na właściwości, łamie to binarną kompatybilność: każdy klient, który użyje twojego kodu/biblioteki, będzie musiał ponownie skompilować.

To jest złe, ponieważ potencjalnie kosztuje dużo pieniędzy.

Korzystanie z właściwości od samego początku pozwala uniknąć tego problemu. Nawet liczy się kod, który nie jest częścią biblioteki. Czemu? Ponieważ nigdy nie wiadomo: kod (nawet jeśli jest wysoce zależny od domeny!) Może okazać się przydatny, więc chcesz go przekształcić w bibliotekę. Ten proces refaktoryzacji jest oczywiście znacznie łatwiejszy, jeśli już korzystasz z właściwości zamiast pól publicznych/chronionych.

Dodatkowo, pisząc publicznych właściwości jest łatwy w C# 3.0, ponieważ można po prostu użyć właściwości auto-wdrożone, oszczędzając sporo kodu:

public DataType MyProperty { get; set; } 

wdroży pole oporowe konieczne i getter/setter Kod dla ciebie.

Dodam notatkę osobistą: zachowanie .NET w tym zakresie jest nieco leniwe. Kompilator może po prostu zmienić publiczne pola na właściwości w locie, unikając w ten sposób problemu. VB6 zrobił to już dla klas narażonych na COM i nie widzę absolutnie żadnego powodu, żeby VB.NET i C# nie robili tego samego. Być może ktoś z zespołów kompilatorów (Jared?) Może komentować to.

+1

Zignorowanie pytania powinno być spowodowane wieloma przyczynami, dla których kompilator nie może tego zrobić. Są 2 powody, które przychodzą nam na myśl. 1) nazwy i 2) wywoływanie właściwości nie jest tym samym, co dostęp do pola (wydajność, ref i out). Niestety nie ma tu wystarczająco dużo miejsca, aby naprawdę komentować – JaredPar

+2

(cd) i wątek jest zamknięty. Ale krótka wersja to użytkownik, który prosi o jeden przedmiot i dajesz mu zastępczą wymianę. Użytkownicy często są nieszczęśliwi, gdy to robisz. – JaredPar

+0

Dzięki za odpowiedź, Jared. :-) –

3

Jeff Atwood has blogged about it:

Istnieją uzasadnione powody, aby dokonać własność trywialne, dokładnie tak, jak przedstawione powyżej:

  • Odbicie działa inaczej od zmiennych vs właściwości, więc jeśli opierają się na refleksji, że to łatwiejsze wykorzystanie wszystkich właściwości.
  • Nie można ustawić daty względem zmiennej.
  • Zmiana zmiennej na właściwość to a breaking change.

To wstyd, że istnieje tak wiele bezsensownego tarcia między zmiennymi a właściwościami; przez większość czasu robią dokładnie to samo. Kevin Dente zaproponował trochę nowej składni, która dałaby nam najlepsze z obu światów: jeżeli różnica między zmienną i mienia jest taki stały problem, zastanawiam

public property int Name; 

Jeśli jednak bardziej radykalne rozwiązanie jest w porządku. Czy nie moglibyśmy całkowicie odrzucić zmiennych na korzyść nieruchomości? Czy właściwości nie robią dokładnie tego samego, co zmienne, ale mają lepszą kontrolę nad widocznością?

0

Użycie właściwości sprawia, że ​​kod jest bardziej zorientowany na obiekt. Udostępniając zmienne składowe publicznie, ujawniasz swoją implementację.

zobaczyć także ten link z C# 's Programming Guide

3

Zmiana pola do właściwości w przyszłości jest uważany za łamanie zmiana. Pola są uważane za szczegóły implementacji klas, a ich publiczne ujawnienie łamie hermetyzację.

+0

Jest to zmiana przełamująca tylko wtedy, gdy kod wywołujący nie może zostać zrekompilowany, przez większość czasu posiadasz kod wywołujący i jest on kompilowany przez ten sam system kompilacji. W związku z tym nie stanowi to problemu dla większości stron z zewnątrz zespołu platformy .NET. –

+0

@Ian Ringrose: Nie jest też całkowicie kompatybilny ze źródłami. Na przykład twój kod może zrobić 'ref obj.MyField'. Nie możesz zmienić 'MyField' na' MyProperty' bez zmiany źródła. –

+0

@Ian: To przełomowa zmiana - http://msdn.microsoft.com/en-us/library/ms182141(VS.80).aspx – Cerebrus

2

Jeśli pracujesz w zamkniętym środowisku - nie tworzysz pakietu SDK, wszystkie klasy są używane w ramach tego samego projektu - nie ma żadnej różnicy.

Zwykłym argumentem jest to, że "w przyszłości może zajść potrzeba sprawdzenia wartości, aby łatwiej było z właściwościami". W ogóle go nie kupuję.

Korzystanie z pól publicznych jest bardziej czytelne, mniej dekoracyjne i łatwiejsze w użyciu.

+0

"Łatwiejszy w użyciu?", Jak to możliwe? –

0

Tak.

Weź pod uwagę publiczny varibale, który ma teraz ciąg znaków, możesz go po prostu ustawić. Jeśli jednak zdecydujesz, że ta publiczna zmienna powinna zawierać obiekt, który powinien zostać zainicjalizowany za pomocą ciągu znaków, musisz zmienić cały kod przy użyciu oryginalnego obiektu. Ale gdybyś użył setera, musiałbyś tylko zmienić ustawiacz, aby zainicjować obiekt za pomocą podanego łańcucha.

1

Można również chronić dostęp do zapisu i zezwalać na odczyt z właściwością:

public int Version { get; private set; } 
+0

To właściwie nie kompiluje. Myślę, że masz na myśli: 'public int Version {get; prywatny zestaw; } ' –

7

w pigułce:

  • można kontrolować acces (tylko do odczytu,
    do zapisu, odczytu/zapisu)
  • Możesz zweryfikować wartości, ustawiając właściwość (sprawdź zero itd.)
  • Możesz wykonaj dodatkowe przetwarzanie, , takie jak leniwy inicjowanie
  • Możesz zmienić podstawową implementację . Na przykład, właściwość może być teraz wspierana przez zmienną członka , ale można ją zmienić , aby była ona wspierana przez wiersz DB bez utraty kodu użytkownika przez .
Powiązane problemy