前几天敲完了机房收费系统的上下机过程,认为很有必要总结一下。心态也好,经验也好,代码也好,我都很想拿出来跟大家分享一下。
心态:
不要被困难吓倒,方法总比困难多。
关于这个上下机的过程自己敲了大概三次,其实到现在为止也不是很满意,至少基本功能算是实现了,总觉得代码可以更少。目前我也只能做到这个份儿上了。。刚开始敲上下机过程的时候,列出了需要的数据,那N个表中的N个数据,着实的令我头疼。然后就是不想啊不想啊不想继续了,对这个系统开始产生恐惧感了,怀疑自己脑袋不好用+_+。。最后支持我去打到困难的原因竟然是,我不想今目标延期。。我就一鼓作气,碰壁,换思路,碰壁,换思路。可算是在预期的时间内完成了上下机。所以,当遇到困难的时候,想的越少的人(这里的想是指胡思乱想)会越早跳出这个困难的圈套。
再来。
经验:
全局观,从大到小。
打个比方就是我们的思维方向应该和大树的生长方向是一致的。从根部(一)开始慢慢的拓展,越想越全面,越想越具体(多)。不能从树叶开始找规律,那样的话,哪会儿才能找到主干呢?我开始就犯了大错误,一直在考虑着余额这么更新啊,临时用户和固定用户收费标准不一样啊,最少上机时间内不收费啊,等等一系列的问题。貌似考虑的很多,其实就是左想想右想想,没有全局观意识,太爱从小方面较劲,半天一行代码也敲不出来。所以具体到每个功能块的实现,都应该从整体把控好,先画一个大概的逻辑图出来,成功率会大大的提高的。
再来。
我还不是很满意的代码。。
一、首先呢先了解一下上下机的实质,就是消费!公式呢就是小学生都懂的:
下机后的钱=上机前的钱-单位消费金额*消费时间
二、然后分析一下这些数据都是从哪些表中获取的,按照公式算完了之后在放回数据到哪些表中:
数据来源:
BasicData_Info(单位金额,最少上机时间)
Student_Info(旧金额)
Online_Info(上机日期,上机时间)
在此只是强调一下分析思路,所以那些其他信息的获取(如学生学号,卡号是否存在等)就不强调了。
数据录入:
Student_Info(新金额)
Line_Info(消费时间,消费金额,下机日期,下机时间)
三、数据的来龙去脉分析清楚了,下面就具体看一下这个数据进出的细节。
上机就是一个基本操作:Student_Info→Online_Info
下面是主要代码的展示:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> '从Student表中获得各个文本框中需要的信息 TxtSQL = "SELECT * From student_info where cardno='" & txtCardNo & "'" Set Stumrc = ExecuteSQL(TxtSQL, MsgText) txtType = Trim(Stumrc.Fields(14)) txtStudentNo = Trim(Stumrc.Fields(1)) txtName = Trim(Stumrc.Fields(2)) txtDepartment = Trim(Stumrc.Fields(4)) txtSex = Trim(Stumrc.Fields(3)) txtOnDate = Format(Date, "yyyy-mm-dd") txtOnTime = Format(Time, "hh:mm:ss") txtCash = Trim(Stumrc.Fields(7)) txtHello.Caption = "~欢迎光临~" Stumrc.Close '将信息写入Online表中 TxtSQL = "SELECT * From Online_Info" Set Onmrc = ExecuteSQL(TxtSQL, MsgText) Onmrc.AddNew Onmrc.Fields(0) = Trim(txtCardNo) Onmrc.Fields(1) = Trim(txtType) Onmrc.Fields(2) = Trim(txtStudentNo) Onmrc.Fields(3) = Trim(txtName) Onmrc.Fields(4) = Trim(txtDepartment) Onmrc.Fields(5) = Trim(txtSex) Onmrc.Fields(6) = Trim(Format(txtOnDate, "yyyy-mm-dd")) Onmrc.Fields(7) = Trim(Format(txtOnTime, "hh:mm:ss")) Onmrc.Fields(8) = Trim(VBA.Environ("ComputerName")) Onmrc.Fields(9) = Trim(Now) Onmrc.Update txtOnNum.Caption = Onmrc.RecordCount '刷新在线人数 Onmrc.Close</strong></span>
上机的问题解决了,其实数据的读写主要是在这个百般纠结的下机过程。我来分步骤消灭一下这个纠结的过程:
①根据用户类型获取BasicData_Info 表数据
这一阶段我们要获取单位金额,和最小上机时间。
主要代码:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> TxtSQL = "SELECT * From Student_Info Where cardno='" & txtCardNo & "'" '从Student表中获得用户信息 Set Stumrc = ExecuteSQL(TxtSQL, MsgText) strType = Trim(Stumrc.Fields(14)) '获得用户的类型,用以判断单位价格定多少 OldCash = Val(Trim(Stumrc.Fields(7))) '获得用户的余额 TxtSQL = "SELECT * From BasicData_Info" '从BasicData表中获得计算数据 Set BasMrc = ExecuteSQL(TxtSQL, MsgText) Leasttime = Val(Trim(BasMrc.Fields(3))) '获得用户最少消费时间 If strType = "固定用户" Then '固定用户每单位消费金额 strRate = Val(Trim(BasMrc.Fields(0))) Else '临时用户每单位消费金额 strRate = Val(Trim(BasMrc.Fields(1))) End If </strong></span>
②获取Online_Info表中的数据
这里用到了一个时间函数DateDiff(),只要输入两个时间点,它就可以计算出我们需要的时间段,我们用它计算消费时间的。具体的我就不解释了,大家自行Baidu吧。这一阶段我们要获得消费时间。
下面是主要代码的展示:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> TxtSQL = "SELECT * From OnLine_Info where cardno='" & txtCardNo & "'" Set Onlmrc = ExecuteSQL(TxtSQL, MsgText) '从Online表中获得上机时间 StartTime = Format(Onlmrc.Fields(7), "HH:mm:ss") '上机时间获取 EndTime = Format(Time, "hh:mm:ss") '下机时间now txtOffDate = Date '文本框显示下机日期 txtOffTime = Time '文本框显示下机时间 txtType = Trim(Onlmrc.Fields(1)) '显示信息 txtStudentNo = Trim(Onlmrc.Fields(2)) txtName = Trim(Onlmrc.Fields(3)) txtDepartment = Trim(Onlmrc.Fields(4)) txtSex = Trim(Onlmrc.Fields(5)) txtOnDate = Trim(Onlmrc.Fields(6)) txtOnTime = Trim(Onlmrc.Fields(7)) txtTime.Text = DateDiff("n", Trim(StartTime), Trim(EndTime)) 'Datediff()函数计算消费时间 '文本框显示消费时间,格式为**分钟 </strong></span>
③从Student_Info表中获得上机前的钱
其实在步骤①获取用户类型的时候已经顺便的获取了学生的余额了。
代码见步骤①。
④根据公式做计算,录入Student_Info表,删除Online_Info表中的记录,录入Line_Info表。
主要代码如下:
做计算:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> '===============消费计算公式:新余额=旧余额-(消费时间*单位消费金额)================== If Val(Trim(txtTime.Text)) <= Leasttime Then '消费小于最短时间,不计费 NewCash = OldCash txtConsume = "0.0" Else If Val(Trim(txtTime)) <= 60 And Val(Trim(txtTime)) > Leasttime Then NewCash = Val(OldCash) - Val(strRate) * 1 txtConsume = strRate & ".0" Else '消费大于最短时间,计费 intTime = Val(txtTime) / 60 NewCash = Val(OldCash) - Val(strRate) * intTime txtConsume = intTime * Val(strRate) & ".0" End If End If </strong></span>
录入Student_Info表:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> txtCash = Trim(NewCash) TxtSQL = "UPDATE student_info set cash=" & NewCash & " where cardno='" & txtCardNo & "'" Call ExecuteSQL(TxtSQL, MsgText) '刷新余额,录入Student表中 </strong></span>
删除Online_Info表:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> TxtSQL = "DELETE Online_Info where cardno='" & txtCardNo & "'" Call ExecuteSQL(TxtSQL, MsgText) '刷新Online表中的数据 TxtSQL = "SELECT * From OnLine_Info" Set Nummrc = ExecuteSQL(TxtSQL, MsgText) txtOnNum.Caption = Nummrc.RecordCount '获得当前在线人数 </strong></span>
录入Line_Info表:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> TxtSQL = "SELECT * From Line_Info" '将信息录入到line表中 Set LMrc = ExecuteSQL(TxtSQL, MsgText) LMrc.AddNew LMrc.Fields(1) = Trim(txtCardNo) LMrc.Fields(2) = Trim(txtStudentNo) LMrc.Fields(3) = Trim(txtName) LMrc.Fields(4) = Trim(txtDepartment) LMrc.Fields(5) = Trim(txtSex) LMrc.Fields(6) = Trim(Format(txtOnDate, "yyyy-mm-dd")) LMrc.Fields(7) = Trim(Format(txtOnTime, "hh:mm:ss")) LMrc.Fields(8) = Trim(Format(Date, "yyyy-mm-dd")) LMrc.Fields(9) = Trim(Format(Time, "hh:mm:ss")) LMrc.Fields(10) = Trim(txtTime) LMrc.Fields(11) = Trim(txtConsume) LMrc.Fields(12) = Trim(NewCash) LMrc.Fields(13) = "正常下机" LMrc.Fields(14) = Trim(VBA.Environ("ComputerName")) LMrc.Update LMrc.Close </strong></span>
四、选中全部学生下机
选中全部学生下机也没什么难的,一个的都会了,多个的那还不简单嘛。一到多转变,马上就想起dim a as integer 和dim a()as integer。
Bingo~就是动态数组,我们先定义个a(),动态数组原则:先预定后设定。
下面是主要代码:
<span style="font-family:KaiTi_GB2312;font-size:18px;"><strong> Dim a() As Integer Dim StuNum As Integer Dim i As Integer TxtSQL = "select count(*) from online_info" Set Onlmrc = ExecuteSQL(TxtSQL, MsgText) StuNum = Trim(Onlmrc.Fields(0)) '获取在线学生的人数 ReDim a(StuNum) '重新定义数组 Onlmrc.Close TxtSQL = "SELECT * From Online_Info" Set Onlmrc = ExecuteSQL(TxtSQL, MsgText) Onlmrc.MoveFirst '从第一个记录集开始进入循环 For i = 0 To StuNum - 1 a(i) = Trim(Onlmrc!cardno) If Onlmrc.EOF Then Exit For End If Onlmrc.MoveNext Next i </strong></span>
小结:
心细的同学可能发现了我这一到四的步骤是逐步细化的,就是我所说的全局观,从大到小。这些思想,只有你真正实践了,才能体会的到。