技术开发 频道

基于C# winfrom的水果店结账系统实现

  【IT168技术】 现实生活中,结账系统无处不在,屡见不鲜,各种结账系统 例如:订餐结账系统,超市购物结账系统,酒店客房结账系统等.其实结账原理都大同小异,即将所有购买项的价格都相加,当然 那些复杂的系统 所考虑的方面和功能就很多了. 我们这里不考虑.

  那么,今天我们这里简单的写个基于C# winform 平台的水果店结账系统.

  原理

  这里用到了一个主窗体类和一个构造函数类(用于存取物品的属性). 还有一个写有物品属性的文本文件(目的是方便后期更改物品的价格,折扣等属性)

  首先,通过FileStream 的OpenRead方法 来打开并读取文本文件, 然后调用 StreamReader来 读取FileStream的字符 并将里面的字节转换成字符串。具体FileStream 和 StreamReader的用法可以参考这里. 从文本里获取到物品的属性之后 将其存到一个具有物品属性的数据结构的泛型list里.

  然后在各个物品按钮下调用 不同物品 其在泛型list里的索引也是不一样的. 然后在用一个整型 数组来存 每个物品按钮的点击次数,即为每个物品的购买次数,还用到一个泛型list 来装载每个物品的价格, 在计算总价的时候 遍历 相加, 得到一个总价.

  这里还用到了一个优惠价,即每个物品都有不同的打折方式(代码里有详细注释), 用到了 一些简单的算法. 并且在结账的时候 自动计算 每项物品最终优惠了多少.

  最后用总价-优惠价=最终我们应该支付的价格. 当然这里也实现了物品清空的功能.

  界面设计

  fruits.txt文本内容

  代码如下

  ProductAttribute.cs 类里的代码

1 using System;
2 using System.Collections.Generic; 3 using System.Linq;
4 using System.Text;
5  
6 namespace 水果店结账系统
7 ...{
8     //这里用到了 一个构造函数 即方法与类同名 9     class ProductAttribute
10     ...{
11         //初始化各值
12         string name = "";
13         float price = 0;
14         int code1 = 0;15         int code2 = 0;
16         //构造方法
17         public ProductAttribute(string n, float p, int c1, int c2)
18         ...{
19             //实现ProductAttribute的数据结构 20             //里面可以传入如下参数21             name = n;
22             price = p;
23             code1 = c1;
24             code2 = c2;
25         }
26         //可以读取ProductAttribute里的Name 属性
27         public string Name28         ...{
29             get ...{ return name; }
30         }
31         //可以读取ProductAttribute里的Price 属性
32         public float Price33         ...{
34             get ...{ return price; }35         }
36         // 一个save方法 用于判断 不同的折扣方式 并返回一个减去的钱数
37         public float save(int n)38         ...{39             float m = 0;  //m用于获取 打折后的 价格 符合的物品数量
40             switch (code1)
41             ...{
42                 case 0: //code1为0 的时候 43                     m = n;  //买多少斤 最终价格还是 按多少斤算
44                     break;
45                 case 1: //code1为1的时候 有2种情况
46                     if (code2 == 0)  //code2为0  买1斤 第2斤免费 即买一送一 47                         m = (float)((n / 2) + (n % 2));  //买1斤 第2斤免费  但买3斤 还是1斤免费 48                     else if (code2 == 1) //code2为1  这里是买1斤 第2斤半价 即买2斤 1斤半的钱  买4斤 3斤的钱
49                         m = (float)(1.5 * (n / 2) + (n % 2));
50                     break;
51                 case 2:   //code1 为2的时候 也有2种方法
52                     if (code2 == 0)  //code1为2 code2 为0 买2斤 第3斤免费
53                         m = (float)(n - (n / 3));
54                     else if (code2 == 1) //code1为2  code2为1 即买2斤 第3斤半价
55                         m = (float)(n - 0.5 * (n / 3));
56                     break;
57             }
58
59             float save = (n - m) * price; //计算出一个最终的价格
60             return save;  //返回省去的钱数
61         }
62     }
63 }

  主窗体类代码 frmFruitShopping.cs

  1 using System;
  
2 using System.Collections.Generic;
  
3 using System.ComponentModel;
  
4 using System.Data;
  
5 using System.Drawing;
  
6 using System.Linq;
  
7 using System.Text;
  
8 using System.Windows.Forms;
  
9 using System.IO; 
10
11 namespace 水果店结账系统
12 {
13     public partial class frmFruitShopping : Form
14     {
15         // new 一个泛型list 里面装载了 ProductAttribute的构造函数
16         List<ProductAttribute> productList;
17         public frmFruitShopping()
18         {
19             InitializeComponent();
20             //在窗体加载的时候 触发它
21             productList = new List<ProductAttribute>();
22             string strRead; //创建一个字符串 用来接受读取的数据
23             // 创建FileStream文件流 可以用来读取任何文件 其内部读取格式是 最原始的字节
24             FileStream fs = File.OpenRead("fruits.txt");
25             //通过流读取来读取fs文件里的东西,并将 文字格式设置为默认的ANSI编码
26             StreamReader sr = new StreamReader(fs, Encoding.Default);
27             //用while循环来 一行行读取  如果读到的内容不为空 则进入循环 否则不读
28             while ((strRead = sr.ReadLine()) != null)
29             {
30                 //这里用到了个字符串分割 每行都有几个参数 通过'-' 隔开 分割后存到一个数组里
31                 string[] part = strRead.Split('-');
32                 //new一个 构造方法来装载 这些参数
33                 ProductAttribute pa = new ProductAttribute(part[0], (float)Convert.ToDouble(part[1]),
34                     Convert.ToInt32(part[2]), Convert.ToInt32(part[3]));
35                 //将 装载的参数 存到 一个装有数据结构的泛型list中
36                 productList.Add(pa);
37             }
38             sr.Close(); //当读取完数据后 关闭读取器 节省内存
39         }
40         //用一个浮点型的list泛型 来装载 所有的开销
41         List<float> TotalCost = new List<float>();
42         //定义一个 可以容纳12个整数的整型数组 用于装载 每样产品的点击数
43         int[] intQuantity = new int[12];
44         //printCost() 方法 用于记录按钮点击数(即每样物品的购买数) 以及在listbox中打印出 购买物品和价格
45         //同时把 购买的物品 添加到 泛型list里 方便后期计算总价
46         public void printCost(int i)
47         {
48             intQuantity[i]++;
49             lstMenu.Items.Add("您购买了\t" + productList[i].Name + "\t " + productList[i].Price + "元/斤");
50             TotalCost.Add(productList[i].Price);
51         }
52
53         //每个按钮下 都调用了一个 printCost();方法
54         //传入的整型参数 是购物品在泛型里的位置 同时也是 intQuantity的索引位置
55         private void btnApple_Click(object sender, EventArgs e)
56         {
57             printCost(0);
58         }
59
60         private void btnOrange_Click(object sender, EventArgs e)
61         {
62             printCost(1);
63         }
64
65         private void btnPear_Click(object sender, EventArgs e)
66         {
67             printCost(2);
68         }
69
70         private void btnbanana_Click(object sender, EventArgs e)
71         {
72             printCost(3);
73         }
74
75         private void btnHawthorn_Click(object sender, EventArgs e)
76         {
77             printCost(4);
78         }
79
80         private void btnHoneyPeach_Click(object sender, EventArgs e)
81         {
82             printCost(5);
83         }
84
85         private void btnCoconut_Click(object sender, EventArgs e)
86         {
87             printCost(6);
88         }
89
90         private void btnFig_Click(object sender, EventArgs e)
91         {
92             printCost(7);
93         }
94
95         private void btnGrape_Click(object sender, EventArgs e)
96         {
97             printCost(8);
98         }
99
100         private void btnLitchi_Click(object sender, EventArgs e)
101         {
102             printCost(9);
103         }
104
105         private void btnPlum_Click(object sender, EventArgs e)
106         {
107             printCost(10);
108         }
109
110         private void btnPomelo_Click(object sender, EventArgs e)
111         {
112             printCost(11);
113         }
114         //在结账按钮下 计算账单
115         private void btnTotal_Click(object sender, EventArgs e)
116         {
117             //遍历 泛型里所有的值 全部加起来
118             float tCost = 0;
119             foreach (float cost in TotalCost)
120             {
121                 tCost += cost;
122             }
123             lstMenu.Items.Add("------------------------");
124             lstMenu.Items.Add("优惠前总价为:\t\t " + Math.Round(tCost,1) + ""); //打印出总价(打折前的价格)
125             //调用Saving()方法 计算 总共节省的钱数
126             float totalSaving = Saving();
127             lstMenu.Items.Add("打折后最终您需要付款为\t " + Math.Round((tCost - totalSaving), 1) + "");
128 129         }
130         // Saving()方法
131         float tSaving = 0;
132         public float Saving()
133         {
134             for (int i = 0; i <= intQuantity.Length - 1; i++)
135             {   //当物品 购买数 >= 2的时候 才有优惠  
136                 if (intQuantity[i] >= 2)
137                 {   //这里 苹果和无花果 是不存在优惠的
138                     if (productList[i].Name == "苹果" || productList[i].Name == "无花果")
139                         lstMenu.Items.Add("您购买了" + productList[i].Name + " 一共" + intQuantity[i] + ""
140                             + " 最近" + productList[i].Name + "无优惠");
141                     else //否则其他水果 都有优惠
142                     {
143                         lstMenu.Items.Add("您购买了" + productList[i].Name + " 一共" + intQuantity[i] + ""
144                             + " 优惠" + Math.Round(productList[i].save(intQuantity[i]), 1) + "");
145                         tSaving += productList[i].save(intQuantity[i]);
146                     }
147                 }
148                 //当购买单项 水果 小于2斤的时候 是没有优惠享受的
149                 else if (1 <= intQuantity[i] && intQuantity[i] < 2)
150                 {
151                     lstMenu.Items.Add("您购买了" + productList[i].Name + " 只有"
152                         + intQuantity[i] + "" + " 没有优惠!");
153                 }
154             }
155             //最终 打印出 所有物品节约的 总价
156             lstMenu.Items.Add("--------------------------------------");
157             lstMenu.Items.Add("所有水果一共优惠了\t " + tSaving + "");
158 159             return tSaving;
160         }
161162         private void btnEmpty_Click(object sender, EventArgs e)
163         {
164             lstMenu.Items.Clear();  //清空list里面的所有项(表面清除)
165             TotalCost.Clear();      //清空泛型list里的所有项(从系统中移除)
166             tSaving = 0;  //把之前节省的钱 全部清空  
167             //清空的时候 要将打折省去的钱数 也清掉
168             //这里用的是 清空所有购买水果的数量 当水果数为0的时候 就没有打折省去的钱数了
169             for (int i = 0; i < intQuantity.Length; i++)
170                 intQuantity[i] = 0;
171         }
172 173         //---这里删除单项 只做到了 总价里面减少 没做到从优惠里减少---//
174         private void btnDeleteOne_Click(object sender, EventArgs e)
175         {
176             //从listbox 里移除 购买项 (表面移除, 实际值需要从装载值的list泛型里移除)
177             lstMenu.Items.Remove(lstMenu.SelectedItem);
178             //SelectedIndex 是从0开始的索引 但实际你删除项的索引是大于0的整数
179             //从泛型list里 移除购买项
180             TotalCost.RemoveAt(lstMenu.SelectedIndex + 1);
181         }
182     }
183 }

  运行效果 如下

  ①结账

  ②清空购物


 

         ③再点结账 看下 确实所有值 都被清空了 (清空购物车 功能没问题)

  ④但是删除单项 这里出问题了 请看下面

  ⑤删除2项 山楂后 总价虽然正常减少了 而且 删除了2斤山楂 山楂的优惠价没变

  而且总优惠价格 也是不但没减少 还把之前的再次相加了一次 导致最终价格不正常 (可能还有一些问题没有发现)。

       源码下载:水果店结账系统 

0
相关文章