Windows 開發慣用 .ini 檔案儲存程式狀態(視窗座標、資料庫連線參數等)。Java 雖無原生 .ini API,但 java.util.Properties 提供了更純粹、跨平台的鍵值對持久化方案——本質是 UTF-8 純文字檔,格式 key=value,人類可讀、版控友好。
| 方法 | 用途 |
|---|---|
load(InputStream) | 從輸入流載入屬性(檔案 → 記憶體) |
store(OutputStream, String) | 寫入輸出流(記憶體 → 檔案),第二參數為註解 |
getProperty(key) | 取得值,找不到回傳 null |
setProperty(key, value) | 設定值(字串專用,避免 Hashtable 原始 put 型別擾亂) |
try {
Properties props = new Properties();
props.load(new FileInputStream("mysave.properties"));
// 注意:getProperty 回傳 String,需轉型
int width = Integer.parseInt(props.getProperty("frame.width", "800"));
int height = Integer.parseInt(props.getProperty("frame.height", "600"));
int x = Integer.parseInt(props.getProperty("frame.x", "100"));
int y = Integer.parseInt(props.getProperty("frame.y", "100"));
frame.setSize(width, height);
frame.setLocation(x, y);
} catch (IOException | NumberFormatException e) {
// 首次啟動或檔案損壞時使用預設值
frame.setSize(800, 600);
frame.setLocation(100, 100);
}
frame.addWindowListener(new WindowAdapter() {
@Override
public void windowClosing(WindowEvent e) {
try {
Properties props = new Properties();
props.setProperty("frame.width", String.valueOf(frame.getWidth()));
props.setProperty("frame.height", String.valueOf(frame.getHeight()));
props.setProperty("frame.x", String.valueOf(frame.getX()));
props.setProperty("frame.y", String.valueOf(frame.getY()));
props.store(new FileOutputStream("mysave.properties"),
"Window Geometry - Auto Saved");
} catch (IOException ex) {
ex.printStackTrace(); // 記錄日誌,不中斷關閉流程
}
System.exit(0);
}
});
System.getProperty("user.home") 或 Preferences API 定位用戶目錄(如 ~/.myapp/config.properties)。load/store 預設 UTF-8,舊版本可能用 ISO-8859-1。建議顯式使用 load(new InputStreamReader(is, StandardCharsets.UTF_8))。Properties 繼承 Hashtable 同步,但複合操作(檢查-修改)仍需外部同步。JSON (Jackson/Gson) 或 Preferences API(系統級註冊表/目錄服務)。Properties 以極簡 API 解決配置持久化核心需求:零依賴、跨平台、人類可讀。配合 try-with-resources 與預設值處理,即可構建健壯的「程式記憶」機制。下次使用者重開應用,視窗依舊停留在上次關閉的位置——這正是細節體驗的開始。