Właśnie zdałem sobie sprawę, że konstrukcja właściwości C # może być również używana z modyfikatorem dostępu prywatnego :
private string Password { get; set; }
Chociaż jest to technicznie interesujące, nie mogę sobie wyobrazić, kiedy z niego skorzystam, ponieważ prywatne pole wymaga jeszcze mniej ceremonii :
private string _password;
i nie mogę sobie wyobrazić, kiedy kiedykolwiek będę musiał być w stanie uzyskać wewnętrznie, ale nie ustawić lub ustawić, ale nie uzyskać prywatnego pola:
private string Password { get; }
lub
private string Password { set; }
ale być może istnieje przypadek użycia z klasami zagnieżdżonymi / dziedziczonymi lub może gdzie get / set może zawierać logikę zamiast po prostu zwracać wartość właściwości, chociaż starałbym się zachować właściwości ściśle proste i pozwolić jawnym metodom na wykonywanie dowolnej logiki, np GetEncodedPassword()
.
Czy ktoś korzysta z własności prywatnych w języku C # z jakiegokolwiek powodu, czy jest to tylko jedna z tych technicznie możliwych, a jednak rzadko używanych w rzeczywistych konstrukcjach kodu?
Uzupełnienie
Dobre odpowiedzi, czytając je Wyrzuciłem te zastosowania dla prywatnych nieruchomości:
- kiedy pola prywatne muszą być ładowane leniwie
- gdy pola prywatne wymagają dodatkowej logiki lub są obliczonymi wartościami
- ponieważ prywatne pola mogą być trudne do debugowania
- w celu „przedstawienia sobie umowy”
- do wewnętrznej konwersji / uproszczenia odsłoniętej właściwości w ramach serializacji
- zawijanie zmiennych globalnych do wykorzystania w twojej klasie
źródło
Odpowiedzi:
Używam ich, jeśli potrzebuję buforować wartość i chcę leniwie ją załadować.
źródło
return _password ?? (_password = CallExpensiveOperation());
return _password ?? (_password = CallExpensiveOperation());
. A właściwie Resharper woli :).private string Password => _password ?? (_password = CallExpensiveOperation());
private string Password => _password ??= CallExpensiveOperation();
CallExpensiveOperation();
jest wywoływane podczas budowy / inicjalizacji zawierającego obiekt, a nie przy pierwszym dostępie do właściwości.Głównym zastosowaniem tego w moim kodzie jest leniwa inicjalizacja, jak wspomnieli inni.
Innym powodem własności prywatnej nad polami jest to, że właściwości prywatne są znacznie łatwiejsze do debugowania niż prywatne pola. Często chcę wiedzieć, że „to pole jest ustawiane nieoczekiwanie; kto jest pierwszym dzwoniącym, który ustawia to pole?” i jest o wiele łatwiej, jeśli możesz po prostu ustawić punkt przerwania na seterze i nacisnąć go. Możesz tam zalogować się. Możesz tam umieścić wskaźniki wydajności. Można wprowadzić kontrole spójności, które działają w kompilacji debugowania.
Zasadniczo sprowadza się to do: kod jest znacznie potężniejszy niż dane . Każda technika, która pozwala mi napisać potrzebny kod, jest dobra. Pola nie pozwalają na pisanie w nich kodu, właściwości tak.
źródło
Osobiście korzystam z tego, nawet jeśli nie potrzebuję logiki na obiekcie pobierającym lub ustawiającym właściwość. Korzystanie z właściwości, nawet prywatnej, pomaga zabezpieczyć kod na przyszłość, aby w razie potrzeby dodać logikę do modułu pobierającego.
Jeśli uważam, że właściwość może w końcu wymagać dodatkowej logiki, czasami zawijam ją do własności prywatnej zamiast używać pola, aby nie musiałem później zmieniać kodu.
W przypadku częściowo powiązanym (choć innym niż twoje pytanie) bardzo często używam prywatnych ustawień w publicznych obiektach:
To daje publiczną metodę pobierania, ale zachowuje prywatność setera.
źródło
Dobrym zastosowaniem dla prywatnych właściwości tylko uzyskać są wartości obliczone. Kilka razy miałem właściwości, które są prywatne tylko do odczytu i po prostu wykonuję obliczenia na innych polach mojego typu. Nie jest wart metody i nie jest interesujący dla innych klas, więc jest to własność prywatna.
źródło
Leniwa inicjalizacja to jedno miejsce, w którym mogą być schludne, np
Następnie możesz napisać:
this.MyType
wszędzie zamiastthis.mytype.Value
i podsumowując fakt, że jest on leniwie utworzony w jednym miejscu.Jedną rzeczą, która szkoda, jest to, że C # nie obsługuje przestawiania zakresu pola właściwości na właściwość (tj. Deklarowanie go w definicji właściwości) w celu całkowitego ukrycia go i zapewnienia, że można uzyskać do niego dostęp tylko za pośrednictwem właściwości.
źródło
field-declaration
y scoped ciąguaccessor-declarations
ma miejsce numer 1 na mojej liście życzeń C # przez długi czas. Jeśli mógłbyś to zaprojektować i wdrożyć w jakiejś (rzeczywistej) przyszłej wersji, to upiec ci ciasto.Jedyne użycie, jakie mogę wymyślić
źródło
private bool IsPasswordSet() { return !String.IsNullOrEmpty(_password); }
Właściwości i pola nie są jeden do jednego. Właściwość dotyczy interfejsu klasy (czy to mówiąc o interfejsie publicznym, czy wewnętrznym), podczas gdy pole dotyczy implementacji klasy. Właściwości nie powinny być postrzegane jako sposób na ujawnienie pól, powinny być postrzegane jako sposób na ujawnienie intencji i celu klasy.
Tak jak korzystasz z nieruchomości w celu przedstawienia konsumentom umowy dotyczącej tego, co stanowi twoją klasę, możesz również przedstawić sobie umowę z bardzo podobnych powodów. Tak, używam własności prywatnych, kiedy ma to sens. Czasami własność prywatna może ukryć szczegóły implementacji, takie jak leniwe ładowanie, fakt, że właściwość jest tak naprawdę konglomeratem kilku pól i aspektów, lub że właściwość musi zostać wirtualnie utworzona przy każdym wywołaniu (pomyśl
DateTime.Now
). Zdecydowanie są chwile, kiedy sensowne jest wymuszanie tego nawet na sobie w zapleczu klasy.źródło
Używam ich w serializacji, z rzeczami takimi jak
DataContractSerializer
lub protobuf-net, które obsługują to użycie (XmlSerializer
nie). Przydaje się, gdy trzeba uprościć obiekt w ramach serializacji:źródło
Jedną rzeczą, którą robię przez cały czas, jest przechowywanie „globalnych” zmiennych / pamięci podręcznej w
HttpContext.Current
źródło
Używam ich od czasu do czasu. Mogą ułatwić debugowanie rzeczy, gdy można łatwo wprowadzić punkt przerwania we właściwości lub dodać instrukcję rejestrowania itp.
Może być również przydatny, jeśli później będziesz musiał w jakiś sposób zmienić typ swoich danych lub będziesz musiał użyć refleksji.
źródło
Korzystam z właściwości prywatnych w celu ograniczenia kodu dostępu do właściwości podrzędnych, z których często korzystam.
Jest to przydatne, jeśli istnieje wiele właściwości podrzędnych.
źródło
Powszechną praktyką jest modyfikowanie członków tylko metodami get / set, nawet prywatnymi. Logika tego jest taka, że wiesz, że get / set zawsze zachowuje się w określony sposób (na przykład odpalanie zdarzeń), co nie wydaje się mieć sensu, ponieważ nie zostaną one uwzględnione w schemacie właściwości ... ale stare nawyki umierają ciężko.
źródło
Ma to sens, gdy istnieje logika związana z zestawem właściwości lub get (pomyśl leniwa inicjalizacja), a właściwość jest używana w kilku miejscach w klasie.
Czy to tylko proste pole zaplecza? Nic nie przychodzi mi na myśl jako dobry powód.
źródło
Wiem, że to pytanie jest bardzo stare, ale poniższe informacje nie zawierały żadnej z aktualnych odpowiedzi.
Jeśli wstrzykujesz swoje zależności, możesz chcieć mieć Gettera na Właściwość, a nie Settera, ponieważ oznaczałoby to właściwość tylko do odczytu. Innymi słowy Właściwość może być ustawiona tylko w konstruktorze i nie może być zmieniona przez żaden inny kod w klasie.
Również Visual Studio Professional poda informacje o właściwości, a nie polu, dzięki czemu łatwiej będzie zobaczyć, jakie pole jest używane.
źródło
Jak nikt nie wspomniał, możesz użyć go do sprawdzania poprawności danych lub blokowania zmiennych.
Uprawomocnienie
Zamykający
Uwaga: Podczas blokowania odniesienia nie blokujesz dostępu do elementów obiektu, do którego istnieje odwołanie.
Leniwe odniesienie: Podczas leniwego ładowania może się okazać, że trzeba go wykonać asynchronicznie, dla którego obecnie istnieje AsyncLazy . Jeśli korzystasz ze starszych wersji niż Visual Studio SDK 2015 lub go nie używasz, możesz również użyć AsyncLazy AsyncEx .
źródło
Niektóre bardziej egzotyczne zastosowania wyraźnych pól obejmują:
ref
lubout
z wartością - być może dlatego, że jest toInterlocked
licznikstruct
z wyraźną układ (może mapować do C ++ wysypisko, albounsafe
kod)BinaryFormatter
automatyczną obsługą pól (zmiana na auto-rekwizyty zmienia nazwy, a tym samym psuje serializator)źródło