C#自定义类数组ItemCount追踪异常问题求助
POS交易记录逻辑问题排查与修复
问题描述
用户需要实现:在ProductsListCBX输入条码后,程序加载对应产品信息;使用TransactionRecord[50]数组存储交易记录(包含ItemCount、ItemName、ItemUnitCost)。当前存在两个问题:
- 新增的交易记录
ItemCount未初始化为0,而是保留上一次交易的值,遍历显示为1、2、3…,预期应为1、1、1… - 条码已存在时,未仅增加对应记录的
ItemCount,反而可能创建新记录
核心问题分析
新Transaction对象初始化时机错误
每次调用CreateTransactionRecord时,先创建TransactionRecord[RecordCount] = new Transaction();,无论条码是否已存在,导致后续循环逻辑混乱,多余创建对象。遍历检查逻辑错误
使用for (int k = 0; k <= RecordCount ; k++)遍历,此时RecordCount指向的是刚创建的空对象,它的条码尚未设置,会触发else分支多次执行IncreaseItemCount(),导致ItemCount被多次累加。Transaction类方法逻辑错误
GetUnitPrice方法错误返回ItemCount * ItemUnitPrice,这是总价的计算逻辑,单价应直接返回ItemUnitPrice。已有记录检查范围错误
检查已有记录时,应该遍历0到RecordCount-1(已存在的有效记录),而不是包含当前刚创建的未初始化记录。
修复后的代码
修改后的POSHubForm.CreateTransactionRecord方法
private void CreateTransactionRecord() { if (ProductListCBX.Text != String.Empty) { try { string itemDataLocation = "D:\\MyApp\\Barcodes\\" + ProductListCBX.Text + ".txt"; SaleItem.LoadProduct(itemDataLocation); saleString += SaleItem.GetPaddedName() + "E" + String.Format("{0:0.00}", SaleItem.GetPrice()) + "\n"; MasterSaleString += SaleItem.GetPaddedName() + "E" + String.Format("{0:0.00}", SaleItem.GetPrice()) + "\n"; ProductInfoLBL.Text = SaleItem.GetName(); totalCost += SaleItem.GetPrice(); MasterCost += SaleItem.GetPrice(); TotalCostLBL.Text = "E" + String.Format("{0:0.00}", totalCost); ItemCostLBL.Text = "E" + String.Format("{0:0.00}", SaleItem.GetPrice()); salesCount++; CountBtn.Text = Convert.ToString(salesCount); bool isExistingItem = false; long currentBarcode = Convert.ToInt64(ProductListCBX.Text); // 先遍历已有的有效记录(0到RecordCount-1) for (int k = 0; k < RecordCount ; k++) { if(currentBarcode == TransactionRecord[k].GetBarCode()) { TransactionRecord[k].IncreaseItemCount(); TransactionRecord[k].SetTotalPrice(); // 更新总价 isExistingItem = true; break; // 找到匹配项后跳出循环 } } // 如果是新商品,创建新的Transaction对象 if (!isExistingItem) { Transaction newTransaction = new Transaction(); newTransaction.SetBarCode(currentBarcode); newTransaction.SetUnitPrice(SaleItem.GetPrice()); newTransaction.SetItemName(SaleItem.GetName()); newTransaction.IncreaseItemCount(); // 初始数量设为1 newTransaction.SetTotalPrice(); TransactionRecord[RecordCount] = newTransaction; RecordCount++; } string Record = String.Empty; string Items = String.Empty; for (int n = 0; n < RecordCount; n++) { Record += TransactionRecord[n].CreateSaleRecord(); Items += Convert.ToString(TransactionRecord[n].GetItemCount()) + ", "; } MessageBox.Show(Record + "\n\n" + Items); ItemDescriptionTBX.Text += " > " + SaleItem.GetName().PadRight(30) + "E" + String.Format("{0:0.00}", SaleItem.GetPrice()) + "\r\n"; } catch (FileNotFoundException) { MessageBox.Show("该产品不存在"); } catch (Exception x) { MessageBox.Show(x.Message); } } else { MessageBox.Show("商品条码不能为空,请输入或选择商品"); } ProductListCBX.Text = String.Empty; }
修改后的Transaction类
using System; namespace MyApp { class Transaction { private long ItemBarCode; private double ItemUnitPrice = 0; private double ItemTotalPrice = 0; private string ItemName = String.Empty; private int ItemCount = 0; public long GetBarCode() { return ItemBarCode; } public string GetItemName() { return ItemName; } public int GetItemCount() { return ItemCount; } // 修复:单价直接返回ItemUnitPrice public double GetUnitPrice() { return ItemUnitPrice; } public double GetTotalPrice() { return ItemCount * ItemUnitPrice; } public string CreateSaleRecord() { return Convert.ToString(ItemCount).PadRight(3) + " x " + ItemName.PadRight(50) + "- E" + String.Format("{0:0.00}", GetTotalPrice()) + "\n"; } public void ReverseItem() { // 可根据需求实现撤销逻辑 } public void IncreaseItemCount() { ItemCount++; } public void DecreaseItemCount() { if(ItemCount > 0) ItemCount--; } public void SetBarCode(long Code) { ItemBarCode = Code; } public void SetItemName(string Name) { ItemName = Name; } public void SetUnitPrice(double Price) { ItemUnitPrice = Price; } public void SetTotalPrice() { ItemTotalPrice = ItemCount * ItemUnitPrice; } } }
修复说明
- 调整逻辑:先遍历已有的有效交易记录,检查条码是否存在,存在则直接增加数量并更新总价
- 仅当条码不存在时,才创建新的Transaction对象,初始化条码、单价、名称后,将数量设为1
- 修复Transaction类的
GetUnitPrice方法,返回正确的单价 - 优化循环范围,避免遍历未初始化的空对象
内容的提问来源于stack exchange,提问作者Bafana Gama
相关产品推荐
相关产品推荐

