一、前言
第 8 次題目集圍繞基礎編程與功能拓展展開。第一題 “點線面重構” 作為基礎題型,核心在于嚴格遵循題目給定的類圖進行代碼實現,將類圖中的類、屬性及關系精準轉化為代碼。實際操作中,主函數的設計是關鍵,需合理完成各類對象的創建、存儲以及結果輸出。第二題 “雨刷程序功能擴展設計”,在原有功能基礎上新增雨刷,要求運用接口和抽象類進行設計,考驗對面向對象設計原則的理解與運用,通過抽象共性行為、定義接口規范,實現代碼的擴展性與可維護性。第三題 “航空貨運管理系統”,雖然輸入信息繁雜,涵蓋客戶、貨物、航班等多方面內容,但計算邏輯清晰,重點在于將業務流程轉化為代碼邏輯,實現運費計算與訂單信息處理功能。?
第 9 次題目集進一步深化面向對象編程的應用。第一題需深入理解類圖中各類的含義與關系,精準把握類的職責與交互邏輯,是對類圖解讀能力的直接考察。第二題 “容器類與泛型”,重點在于掌握容器類的使用及泛型特性,通過泛型實現類型安全,同時實現容器的增刪遍歷等操作,提升數據管理的靈活性與效率。第三題則是對第 8 次題目集航空貨運管理系統的拓展,引入不同類型的貨物與客戶類型,增加了費率計算的復雜性,需要在原有代碼基礎上,結合新的業務規則進行功能擴展,全面考查代碼的擴展性和對復雜業務邏輯的處理能力 。
二、設計與分析
- 第八次題目集
1.點線面問題重構
這道題把將Point類和Line類作為Element類的子類,將Element設置為抽象類,重寫display() 方法,主函數中調用
// 使用 Element 引用實現多態
Element element;
element = p1;//起點Point
element.display();
System.out.println();
element = p2;//終點Point
element.display();
System.out.println();
element = line;//線段
element.display();
element = plane;//面
element.display();
- 用父類引用統一管理子類對象,代碼簡潔。
- 支持后續新增子類(如
Circle),無需修改遍歷邏輯。
2.雨刷重構的設計:
這道題一開始并沒有寫的很順暢,我覺得我的代碼的復雜度很高這道題用switch來直接選擇速度會更好一點,我是用的數組,因為兩個表的間歇檔位的檔位數量不同,所以數組大小也不同。把Agent抽象出來,重寫了兩個方法
// 定義 Agent 接口
interface Agent {
void dealSpeed();
void show(String operationType);
}
3.航空貨運管理系統
題目說明:
https://images.ptausercontent.com/499d204b-fcef-4610-a9ca-c8fbf5e346d9.pdf
本次題目模擬某客戶到該航空公司辦理一次貨運業務的過程:
航空公司提供如下信息:
航班信息(航班號,航班起飛機場所在城市,航班降落機場所在城市,航班
日期,航班最大載重量)
客戶填寫貨運訂單并進行支付,需要提供如下信息:
客戶信息(姓名,電話號碼等)
貨物信息(貨物名稱,貨物包裝長、寬、高尺寸,貨物重量等)
運送信息(發件人姓名、電話、地址,收件人姓名、電話、地址,所選航班號,訂單日期)
支付方式(支付寶支付、微信支付)
注:一個貨運訂單可以運送多件貨物,每件貨物均需要根據重量及費率單獨計費。
程序需要從鍵盤依次輸入填寫訂單需要提供的信息,然后分別生成訂單信息報表及貨物明細報表
這道題目我把運輸類定義為父類Trans,order類整合所有的信息,
// 訂單類(整合所有信息)
class Order extends Trans {
private String orderId;
private Customer customer;
private List<Cargo> cargoList;
private Flight flight;
public Order(String orderId, String orderDate, Customer customer,
List<Cargo> cargoList, Flight flight, Trans transInfo) {
super(transInfo.getSenderName(), transInfo.getSenderPhone(), transInfo.getSenderAddress(),
transInfo.getReceiverName(), transInfo.getReceiverPhone(), transInfo.getReceiverAddress(),
transInfo.getFlightNum(), transInfo.getOrderDate());
this.orderId = orderId;
this.customer = customer;
this.cargoList = cargoList;
this.flight = flight;
}
// Getter 方法
public String getOrderId() {
return orderId;
}
public Customer getCustomer() {
return customer;
}
public List<Cargo> getCargoList() {
return cargoList;
}
public Flight getFlight() {
return flight;
}
}
這個貨物運費加和時運用的方法有點高級,我們可以換成下一種
return cargoList.stream() // 將列表轉換為Stream流
.mapToDouble(Cargo::cal_Money) // 映射每個貨物到其費用
.sum(); // 累加所有費用
private static double calculateTotalCost(List<Cargo> cargoList) {
double total = 0.0;
for (int i = 0; i < cargoList.size(); i++) {
Cargo cargo = cargoList.get(i);
total += cargo.cal_Money(); // 累加單件費用
}
return total;
}
![]()
![]()
- 代碼行數(Lines):465
- 語句數量(Statements):134
- 代碼結構相關(Percent Branch Statements):分支語句所占百分比,為 0.0% ,反映代碼中使用如if - else 、switch等分支結構的比例情況。
- 方法調用語句數量(Method Call Statements):8
- 含注釋的代碼行所占百分比(Percent Lines with Comments):1.9%
- 類和接口的數量(Classes and Interfaces):4
- 平均每個類的方法數(Methods per Class):13.50
- 平均每個方法的語句數(Average Statements per Method): 2.26
- 最復雜方法所在的行號(Line Number of Most Complex Method): 103
- 最復雜方法的名稱(Name of Most Complex Method):Normal
- 最大復雜度(Maximum Complexity): 1
//衡量方法邏輯復雜程度,數值越高邏輯越復雜
平均復雜度(Average Complexity):1.0
類圖:
![]()
分析:
面向對象設計思想明確
-
- 代碼通過多個類(
Trans、Cargo、Customer、Flight、Order)封裝不同領域的概念,符合單一職責原則。
- 使用繼承(如
NormalCargo繼承Cargo)和接口(PaymentMethod)實現多態,例如支付方式可擴展(支付寶、微信支付),符合開閉原則。
模塊化結構清晰
-
- 類職責劃分明確:
Trans負責運輸信息,Cargo處理貨物計算,Flight管理航班信息,Order整合所有數據。
PaymentMethod接口分離支付邏輯,便于后續擴展其他支付方式(如銀聯支付)。
數據校驗與業務邏輯分離
-
- 在
main方法中檢查貨物總重量是否超過航班載重,邏輯清晰,避免業務邏輯混入類內部。
代碼復用性較好
-
Cargo類的calWeight和cal_Money方法可被所有子類繼承,減少重復代碼。
calculateTotalCost靜態方法復用貨物費用計算邏輯。
第九次習題集
1.魔方問題:
類圖:
![]()
弄明白一個類是每一塊體積,下面的類是整個的魔方體積
2.點線面問題的重構
主要是多加了一個容器類和主函數的變化
3.航空貨運管理系統
https://images.ptausercontent.com/b9cec79b-8012-4901-843e-3d48f27d28a6.pdf
![]()
![]()
- 代碼行數(Lines):516
- 語句數量(Statements):214
- 代碼結構相關(Percent Branch Statements):分支語句所占百分比,為 2.3% ,反映代碼中使用如if - else 、switch等分支結構的比例情況。
- 方法調用語句數量(Method Call Statements):45
- 含注釋的代碼行所占百分比(Percent Lines with Comments):9.1%
- 類和接口的數量(Classes and Interfaces):9
- 平均每個類的方法數(Methods per Class):6.22
- 平均每個方法的語句數(Average Statements per Method): 1.43
- 最復雜方法所在的行號(Line Number of Most Complex Method): 16
- 最復雜方法的名稱(Name of Most Complex Method):ALiPay
- 最大復雜度(Maximum Complexity): 1
//衡量方法邏輯復雜程度,數值越高邏輯越復雜
類圖:
![]()
三、踩坑心得
航空貨運系統主要是添加了不同的貨物類,客戶類
![]()
我定義了三種不同貨物的子類 ,Normal/Expedite/Dangerous,重寫費率和運費方法,定義了兩種客戶類型Individual/Corporate,加上獲取折扣率的方法,因為繼承客戶類,直接在Order訂單類中直接 * customer.getDiscountRate();算出單件運費,貨物類相同
主要是在考慮主函數如何輸入,如何創建對象
Customer customer;
if ("Individual".equals(kind)) {
customer = new individualCustomer(customerId, customerName, customerPhone, customerAddress);
} else if ("Corporate".equals(kind)) {
customer = new corporateCostomers(customerId, customerName, customerPhone, customerAddress);
} else {
customer = new Customer(customerId, customerName, customerPhone, customerAddress);
}
//---------------------------------------------------------------------
// 根據貨物類型創建對應實例(修復構造函數調用)
switch (kindCargo) {
case "Normal":
cargoList.add(new NormalCargo(id, name, length, width, height, weight));
break;
case "Expedite":
cargoList.add(new ExpediteCargo(id, name, length, width, height, weight));
break;
case "Dangerous":
cargoList.add(new DangerousCargo(id, name, length, width, height, weight));
break;
default:
throw new IllegalArgumentException("無效的貨物類型");
}
}
另外在提交之后發現答案錯誤,
最后發現是在表格中的實際重量打印成了質量重量,把getWeight();改成calWeight();之后答案正確
四、改進建議
代碼中注釋含量明顯較少,可能需要添加更為詳細的代碼注釋,Order 類職責過多,拆分計算費用的邏輯到單獨的服務類。可以將 Customer 改為接口或抽象類,讓 Order 依賴抽象而非具體類;使用組合代替繼承(Order 和 Trans 的關系)。抽象接口(ICustomer、PaymentMethod)的使用降低高層模塊對具體類的依賴。
五、總結
通過這兩次題目集的實踐,我系統掌握了面向對象編程的核心思想與設計原則。在類的設計上,接口(如PaymentMethod)規范行為,通過繼承與多態實現代碼復用(如不同貨物類型的運費計算)。理解了單一職責原則的重要性,例如將Order的職責拆分為數據存儲與費用計算,提升代碼內聚性。 深刻體會開閉原則“對擴展開放、對修改封閉”的優勢。同時,通過輸入校驗、重量超限檢查等細節,增強了代碼健壯性意識。 此外,認識到命名規范、注釋完整性對代碼可讀性的影響,以及組合優于繼承的設計原則(如`Order`與`Trans`的關系)。