在Java程式設計中,過度的if
巢狀會使程式碼難以閱讀和維護。為了遵循良好的程式碼規範,我們應儘量減少巢狀的深度。這通常可以透過重新組織程式碼或使用其他結構(如switch
語句,或者將邏輯封裝到單獨的方法中)來實現。
以下是一個減少if
巢狀的示例。
示例:使用者身份驗證和許可權檢查
假設我們有一個系統,需要對使用者進行身份驗證,並根據使用者的角色賦予不同的許可權。
不規範的做法(深層巢狀):
public class AccessControl {
public static void checkAccess(User user) {
if (user != null) {
if (user.isAuthenticated()) {
if (user.getRole().equals("admin")) {
System.out.println("Admin access granted.");
} else if (user.getRole().equals("user")) {
System.out.println("User access granted.");
} else {
System.out.println("Access denied.");
}
} else {
System.out.println("User is not authenticated.");
}
} else {
System.out.println("User is null.");
}
}
}
規範的做法(減少巢狀):
public class AccessControl {
public static void checkAccess(User user) {
if (user == null) {
System.out.println("User is null.");
return;
}
if (!user.isAuthenticated()) {
System.out.println("User is not authenticated.");
return;
}
grantAccessBasedOnRole(user);
}
private static void grantAccessBasedOnRole(User user) {
switch (user.getRole()) {
case "admin":
System.out.println("Admin access granted.");
break;
case "user":
System.out.println("User access granted.");
break;
default:
System.out.println("Access denied.");
break;
}
}
}
在這個改進的版本中,我們透過提前返回(return
)來減少巢狀的深度。我們還引入了一個新的方法grantAccessBasedOnRole
來處理基於角色的訪問控制,這進一步提高了程式碼的可讀性和可維護性。
1. 示例中的User
類
為了完整起見,這裡是一個簡單的User
類,用於上述示例:
public class User {
private String name;
private String role;
private boolean authenticated;
public User(String name, String role, boolean authenticated) {
this.name = name;
this.role = role;
this.authenticated = authenticated;
}
public String getName() {
return name;
}
public String getRole() {
return role;
}
public boolean isAuthenticated() {
return authenticated;
}
}
2. 測試程式碼
我們可以使用以下程式碼來測試上述的AccessControl
類:
public class Main {
public static void main(String[] args) {
User admin = new User("Alice", "admin", true);
User user = new User("Bob", "user", true);
User guest = new User("Charlie", "guest", true);
User unauthenticatedUser = new User("David", "user", false);
User nullUser = null;
AccessControl.checkAccess(admin); // 輸出: Admin access granted.
AccessControl.checkAccess(user); // 輸出: User access granted.
AccessControl.checkAccess(guest); // 輸出: Access denied.
AccessControl.checkAccess(unauthenticatedUser); // 輸出: User is not authenticated.
AccessControl.checkAccess(nullUser); // 輸出: User is null.
}
}
首先,我們可以為User
類新增一些更多的屬性和方法,使其更加真實和實用。
3. 擴充套件的User
類
public class User {
private String username;
private String password; // 新增密碼屬性
private String role;
private boolean isAuthenticated;
public User(String username, String password, String role) {
this.username = username;
this.password = password;
this.role = role;
this.isAuthenticated = false; // 初始未認證
}
// Getters and Setters
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getRole() {
return role;
}
public void setRole(String role) {
this.role = role;
}
public boolean isAuthenticated() {
return isAuthenticated;
}
public void setAuthenticated(boolean authenticated) {
isAuthenticated = authenticated;
}
// 新增認證方法
public boolean authenticate(String password) {
if (this.password.equals(password)) {
this.isAuthenticated = true;
return true;
}
return false;
}
}
4. 擴充套件的AccessControl
類
我們可以在AccessControl
類中新增一個登入方法,用於處理使用者的認證。
public class AccessControl {
// ... 之前的程式碼 ...
// 新增登入方法
public static boolean login(User user, String password) {
return user.authenticate(password);
}
}
5. 擴充套件的測試類Main
public class Main {
public static void main(String[] args) {
// 建立使用者並設定初始密碼和角色
User admin = new User("adminUser", "adminPass", "admin");
User user = new User("regularUser", "userPass", "user");
// 嘗試登入並驗證許可權
if (AccessControl.login(admin, "adminPass")) {
System.out.println("Admin logged in successfully.");
checkAccess(admin); // 假設這是一個單獨的方法,用於列印訪問許可權資訊
} else {
System.out.println("Admin login failed.");
}
if (AccessControl.login(user, "userPass")) {
System.out.println("User logged in successfully.");
checkAccess(user); // 假設這是一個單獨的方法,用於列印訪問許可權資訊
} else {
System.out.println("User login failed.");
}
}
// 新增一個方法來檢查並列印使用者訪問許可權資訊
private static void checkAccess(User user) {
if (user.isAuthenticated()) {
switch (user.getRole()) {
case "admin":
System.out.println("Admin access granted. Full permissions.");
break;
case "user":
System.out.println("User access granted. Limited permissions.");
break;
default:
System.out.println("Unknown role. Access denied.");
break;
}
} else {
System.out.println("User is not authenticated. Access denied.");
}
}
}
在這個擴充套件的示例中,我們為使用者新增了一個密碼屬性,並允許使用者透過authenticate
方法進行認證。AccessControl
類現在提供了一個login
方法,用於處理登入邏輯。測試類Main
中,我們建立了兩個使用者(管理員和普通使用者),並嘗試使用正確的密碼登入。登入成功後,我們呼叫checkAccess
方法來驗證和列印出使用者的訪問許可權資訊。
這個示例現在更加完整,並且具有實際的應用價值,因為它模擬了一個簡單的使用者認證和許可權檢查系統。