2010-11-24 62 views
14

我參加過面試。面試官問我爲什麼你需要私人變量。如果通過定義一個變量private來實現某些功能,那麼通過定義java中定義的任何其他訪問修飾符是否可以達到同樣的效果?你如何決定定義一個變量「私人」?

 
According to Java Specification Languages, 

A private class member or constructor is accessible only within the body of the 
top level class (7.6) that encloses the declaration of the member or constructor. 
It is not inherited by subclasses. 

但是,如果我設計一個類,我該如何決定定義一個變量「私人」?

+0

我不明白這個問題。這是爲什麼你想要聲明一個變量私人?是否可以通過其他訪問修飾符或其他訪問修飾符與其他程序更改或約束獲得與`private`相同的效果? – 2010-11-29 19:07:22

回答

40

通過限制「其他代碼」的訪問(可能由他人編寫/維護),您可以更自由地在將來更改它,而不必擔心會破壞依賴它的其他代碼。

問題不在於「我應該讓這個私人?」,而是「是否需要這是非私人的?」。是否有其他可能需要訪問該變量的代碼?

如果事實證明是這樣,您可以指定正確的訪問權限(可能通過獲取者/設置者)並接受對其的更改將很困難。否則你不要私下。

+6

「不是」我應該讓這個私人?「,而是」有沒有需要這是非私人的?「。」我的想法確切。 – WernerCD 2010-11-24 14:39:15

7

一般的經驗法則是減少變量和方法的範圍。你保持私密的東西越多,就越容易改變你的班級,導致系統中其他部分出現問題(例如:減少耦合)。

所以作爲一般規則,私人應該是默認

11

我想你應該看看它從另一個方向:爲什麼你會做出什麼變化,但私人?正確的封裝意味着隱藏你的實現的細節,所以默認應該是使字段私有。

2

成員是私有的情況:

  1. 它是一個屬性,它的閱讀,應該通過類方法只執行寫入
  2. 它的意義只在對象的背景和無處
  3. 它不應該是從類

這樣設計的目的就是封裝,這意味着你已經從客戶端鱈魚牆根類實現外部可見即它提高了代碼的可讀性,可維護性和可測試性。

3

所以,你必須問自己,爲什麼它必須是私人的。那麼,如何通過矛盾觀念來運用真理呢?

它可以公開嗎? 如果答案是,你不希望人們能夠直接訪問和修改屬性,那麼它不能公開。

它可以默認? 如果答案是,你不希望相同的包能夠直接訪問和修改屬性,那麼它不能默認。

它可以被保護 如果答案是,你不希望子類直接訪問和修改屬性,那麼它不能被保護。

因此,如果所有答案都是否定的(並且您必須確定您不希望在這些情況下訪問的答案),那麼它必須是私有的。

問題是,你真的明白修改器給你什麼,以及如何訪問它們,而不是盲目地把所有東西都隱藏起來,並創建setter和getters,因爲這是你的講師/書/手冊教你。

+1

我會假設它應該是私人的,除非它必須有更廣泛的訪問範圍。 – 2010-11-24 12:30:09

3

如果你通過定義一個變量private來獲得某些東西,你能通過定義java中定義的任何其他訪問修飾符來實現嗎?

是的。確實如此。任何private可以更改爲public(或protected等),程序將編譯並運行,就像以前一樣。

訪問修飾符是爲了方便程序員,並幫助他正確定義類的接口。看看the wikipedia article on encapsulation

0

許多這些註釋適用於內部/嵌套類,方法和構造函數。

基本上,您希望儘可能限制訪問而不會造成不必要的複雜性。如果你能做出私人或靜態的東西,我建議你。如果您可以製作最終場地,這通常也有助於提高清晰度。

當一個字段或任何成員是私人的,你可以立即看到它的使用和不再使用的時間。

1

類的主要觀點是封裝數據和行爲並隱藏內部實現,同時在外部暴露乾淨,簡單和有用的API。

有兩個不同的事情要考慮:公共合同(API)和私人數據。

  1. 私人領域:這是您的私人數據,由於以下原因您不希望暴露於外部:安全性和完整性。私有方法:您的實用函數使代碼更具可讀性和可維護性。

  2. 公共方法:您公開給其他人的契約(接口,API)。這就是你的課程有用的原因。

  3. 公共領域:不要使用它。它僅公開部分內部數據。對於簡單的類可能沒問題,而對於具有相互依賴字段的複雜類,這是一個很大的禁忌。爲了公開功能,你應該使用公共方法(第3點)。

8

基本上,一旦你做了一個變量public,你承諾並且永遠不能回頭做這個決定。每一個未來的變化都會改變你班級的公共接口,這意味着每一個班級的使用都需要改變。對於公共API而言,這是不可想象的;您的庫有效打破了向後兼容性。

即使是私人使用的課程,這也是一件大事。

因此,你什麼時候將變量的範圍改爲private?這有很多可以想象的理由。最簡單的是,每當變量的值發生變化時(例如記錄變更或相應地更新其他變量),您的類可能需要執行一些操作。或者你稍後決定,根本不需要該變量,並且用戶請求的值應該被動態計算。

如果您直接閱讀或設置變量,那是不可能的。相反,您的類需要強制用戶調用getter/setter,禁止直接訪問該變量並在其位置提供適當的公共getter/setter方法。

因爲通常你可以永遠預見這樣的未來變化,它已成爲公認的最佳實踐,使沒有變量public每個變量應該是private(或至少內部)。

(有一個例外:在某些情況下,final變量可以安全地進行public例如,枚舉類常量常常實現爲Java庫public final變量,因爲它們永遠不會改變,而且因爲不需要訪問控制。它們是隻讀的)。