【前言】
最近因为公司年会需要,组长让我们花几天时间开发了个抽奖系统。虽然就是cs的一个小例子,不过自己设计算法的过程还是蛮有意思的。下面先给大家看看,最后成品的样子。主要实现的就是excel表的导入导出和抽奖功能, 这篇就讲一下抽奖功能的实现。目前实现的效果是点击开始时,全屏隐去,只剩下名字在滚动显示,需要停止时在datagridview中显示出获奖人信息。
【设计思路】
首先从excel导入名单到dataset,用timer 控制label(lblgetname)每毫秒显示
一个dataset中的名字,循环显示。 然后写一个getname方法, 让timer启动一下,
系统延迟10毫秒,然后停一下,得到一个名字。 再写一个getnewName(string[]
nameSet,string tmpName,int times)方法用来查重,将抽到的名字传进去和
抽到的名字集合nameset做比较,有重复的,重新抽取。 SelectPerson就是调用get
name和getNewName获得抽奖人,然后把已经抽到的人从dataSet中删除,防止多次抽
奖重复抽取一个人。 这是这一版的实现思路,最终成型的和这个又有差别。
【正文】
最初的想法是通过随机数来实现抽奖, 但是到多次抽奖间不重复的时候卡住了, 不知道怎么让随机数产生时刨除确定的几个数。
最后是通过label和timer实现的选人,每选一次就从dataSet中删除一部分人。代码如下:
private void btnBegin_Click(object sender, EventArgs e)
{
label1.Visible = false;
label2.Visible = false;
label3.Visible = false;
txtNumber.Visible = false;
btnLook.Visible = false;
btnBegin.Visible = false;
btnPreserve.Visible = false;
btnResetting.Visible = false;
dgv.Visible = false;
lblgetName.Visible = true;
dgv.Rows.Clear();
if (user != "")
{
if (txtNumber.Text.Trim() != "")
{
lblgetName.Text = "吴迪";
if (ds.Tables[0].Rows.Count > int.Parse(txtNumber.Text) * 1.3)
{
timer1.Start();
btnBegin.Enabled = false;
}
else
{
MessageBox.Show("剩余人数已不足");
lblgetName.Visible = false;
label1.Visible = true;
label2.Visible = true;
label3.Visible = true;
txtNumber.Visible = true;
btnLook.Visible = true;
btnBegin.Visible = true;
btnPreserve.Visible = true;
btnResetting.Visible = true;
dgv.Visible = true;
return;
}
}
else
{
MessageBox.Show("请输入要选出的人数");
}
}
else
{
MessageBox.Show("请导入人员信息!");
}
}
private void lblgetName_Click(object sender, EventArgs e)
{
int number = int.Parse(txtNumber.Text.Trim());
string[] nameSet = selectPerson(number);
try
{
for (int rows = 0; rows <= ds.Tables[0].Rows.Count - 1; rows++)
{
for (int times = 0; times < number; times++)
{
if (ds.Tables[0].Rows[rows][1].ToString().Trim() == nameSet[times].ToString().Trim())
{
ds.Tables[0].Rows[rows][2] = "是";
ds.AcceptChanges();
}
}
}
}
catch (Exception)
{
MessageBox.Show("剩余人数不足", "提示", MessageBoxButtons.OK, MessageBoxIcon.Warning);
}
List<LuckyPerson> luckyPeople = new List<LuckyPerson>();
int reCount = ds.Tables[0].Rows.Count - 1;
for (int rows = 0; rows <= reCount; rows++)
{
if (ds.Tables[0].Rows[rows][2].ToString().Trim() == "是")
{
LuckyPerson lucky = new LuckyPerson();
lucky.Name = ds.Tables[0].Rows[rows][1].ToString().Trim();
//2表示电话所在列
lucky.Tel = ds.Tables[0].Rows[rows][2].ToString().Trim();
luckyPeople.Add(lucky);
}
}
dgv.Rows.Add(luckyPeople.Count);
for (int i = 0; i < luckyPeople.Count; i++)
{
dgv.Rows[i].Cells[0].Value = luckyPeople[i].Name;
dgv.Rows[i].Cells[1].Value = luckyPeople[i].Tel;
}
deletLuky(reCount);
btnBegin.Enabled = true;
label1.Visible = true;
label2.Visible = true;
label3.Visible = true;
txtNumber.Visible = true;
btnLook.Visible = true;
btnBegin.Visible = true;
btnPreserve.Visible = true;
btnResetting.Visible = true;
dgv.Visible = true;
lblgetName.Visible = false;
}
#region 抽奖功能-宋荣凯-2017年3月14日
/// <summary>
///
//抽出幸运观众selectPerson-宋荣凯-2017年3月14日
/// </summary>
/// <param name="times">抽取数量</param>
/// <returns>获奖人的集合</returns>
public String[] selectPerson(int times)
{
String[] nameSet = new String[times];
string nameTmp;
//循环将抽中人员放入集合中
for (int i = 0; i < times; i++)
{
nameTmp = getName();
if (i == 0)
{
nameSet[i] = nameTmp;
}
else
{
//检查是否本次内是否有重复人员
nameSet[i] = getNewName(nameSet, nameTmp, i);
}
}
return nameSet;
}
/// <summary>
/// 若重复重新抽取--getNewName--宋荣凯-2017年3月14日
/// </summary>
/// <param name="nameSet">本次已抽中人</param>
/// <param name="nameTmp">当前抽中人</param>
/// <param name="times">已抽中人数</param>
/// 通过循环递归,将
///
/// <returns>不重复的获奖人</returns>
public String getNewName(String[] nameSet, String nameTmp, int times)
{
int n = 0;
string finalName = "";
while (n < times)
{
if (nameSet[n].ToString().Trim() == nameTmp.ToString().Trim())
{
nameTmp = getName();
finalName = getNewName(nameSet, nameTmp, times);
}
else
{
finalName = nameTmp;
}
n++;
}
return finalName;
}
/// <summary>
/// 抽取获奖人-getName-宋荣凯-2017年3月14日
/// </summary>
/// 通过timer的开关,获取label中的名字
/// <returns>获奖人姓名</returns>
public String getName()
{
string name;
timer1.Start();
Thread.Sleep(100);
System.Windows.Forms.Application.DoEvents();
timer1.Stop();
name = this.lblgetName.Text;
return name;
}
#endregion
//从dataSet中删去已抽中的人
public void deletLuky(int reCount)
{
for (int rows = 0; rows <= reCount; rows++)
{
if (ds.Tables[0].Rows[rows][2].ToString().Trim() == "是")
{
ds.Tables[0].Rows[rows].Delete();
ds.AcceptChanges();
reCount--;
rows--;
}
}
}
private void timer1_Tick(object sender, EventArgs e)
{
if (i > ds.Tables[0].Rows.Count - 1)
{
i = 0;
}
if (ds.Tables[0].Rows[i][1].ToString() != null)
{
this.lblgetName.Text = ds.Tables[0].Rows[i][1].ToString();
}
else
{
i = i + 1;
this.lblgetName.Text = ds.Tables[0].Rows[i][1].ToString();
}
i++;
}
【总结】