可以尝试“减‘大数’不小于零”的方法获得找钱方案。
就是从最大面值的货币开始,用要找退的金额减去货币面额。
如果不小于零,则认为为有效,将找退金额减去面额后继续测试,同时纸币数目加一;
如果小于零,则说明用次面额货币找钱不可行,减小面额后继续测试,纸币数目不加一;
如果等于零,说明找钱结束,纸币数目加一后,返回总共纸币数目即可。
/*
我国现在流通的纸币包扩:100元,50元,20元,10元,5元,2元,1元,5角,2角,1角十种面额,现在用100元人民币买东西,编程确定能找回最少的纸币及方案?
*/
private void button3_Click(object sender, EventArgs e)
{
try
{
double pay = Convert.ToDouble(textBox1.Text);//这里的textbox1是输入的要花的钱。
Listlist = new List ();
huaqian((int)(pay * 10), ref list);//要花费的我给乘10,在变整型。
string msg = "";
for (int i = 0; i < list.Count; i++)
{
string temp = string.Format("面额:{0},数量:{1}\n", list[i].Miane.ToString(), list[i].Count);
msg = msg + temp;
}
MessageBox.Show(msg);
}
catch (Exception)
{
MessageBox.Show("输入的数字有问题,不符合规范。");
}
}
///
/// ~我国现在流通的纸币包扩:100元,50元,20元,10元,5元,2元,1元,5角,2角,1角十种面额
///
public enum MianE
{
///
/// 100元
///
M100,
///
/// 50元
///
M50,
///
/// 20元
///
M20,
///
/// 10元
///
M10,
///
/// 5元
///
M5,
///
/// 2元
///
M2,
///
/// 1元
///
M1,
///
/// 5角
///
M0_5,
///
/// 2角
///
M0_2,
///
/// 1角
///
M0_1
}
///
/// 找零类,某张面额有多少张
///
private class ZhaoLing
{
public ZhaoLing(MianE miane, int count)
{
_miane = miane;
_count = count;
}
MianE _miane;
///
/// 面额
///
public MianE Miane
{
get { return _miane; }
set { _miane = value; }
}
int _count;
///
/// 数量
///
public int Count
{
get { return _count; }
set { _count = value; }
}
}
private void huaqian(int pay, ref Listlist)
{
//首先验证这个要花的钱是1角-99.9元之间
if (pay > 1000)
{
//这样不行的~你只有100元
MessageBox.Show("这样不行的~你只有100元");
}
else if (pay <= 0)
{
//
MessageBox.Show("不花钱,你搞毛,我要罢工。");
}
else
{
//之后,就知道100元应该找回的余额。用这个余额去计算应该找回的面额和数量。
//这个规则就是看余额是否大于最大的面额,大就拿出,否则向下递归
int yue = 1000 - pay;
money(yue, ref list);
}
}
///
///
///
/// 余额转面值的数据
///
private void money(int yue, ref Listlist)
{
if (yue - 1000 >= 0)
{
//这个不应该有直接进入下一个步骤
}
else if (yue - 500 >= 0)
{
if (checkList(MianE.M50,ref list))
{
//在上面的验证中,已经把数量+1了
}
else
{
list.Add(new ZhaoLing(MianE.M50, 1));
}
money(yue - 500, ref list);
}
else if (yue - 200 >= 0)
{
if (checkList(MianE.M20, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
{
list.Add(new ZhaoLing(MianE.M20, 1));
}
money(yue - 200, ref list);
}
else if (yue - 100 >= 0)
{
if (checkList(MianE.M10, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
{
list.Add(new ZhaoLing(MianE.M10, 1));
}
money(yue - 100, ref list);
}
else if (yue - 50 >= 0)
{
if (checkList(MianE.M5, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
list.Add(new ZhaoLing(MianE.M5, 1));
money(yue - 50, ref list);
}
else if (yue - 20 >= 0)
{
if (checkList(MianE.M2, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
list.Add(new ZhaoLing(MianE.M2, 1));
money(yue - 20, ref list);
}
else if (yue - 10 >= 0)
{
if (checkList(MianE.M1, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
list.Add(new ZhaoLing(MianE.M1, 1));
money(yue - 10, ref list);
}
else if (yue - 5 >= 0)
{
if (checkList(MianE.M0_5, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
list.Add(new ZhaoLing(MianE.M0_5, 1));
money(yue - 5, ref list);
}
else if (yue - 2 >= 0)
{
if (checkList(MianE.M0_2, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
list.Add(new ZhaoLing(MianE.M0_2, 1));
money(yue - 2, ref list);
}
else if (yue - 1 >= 0)
{
if (checkList(MianE.M0_1, ref list))
{
//在上面的验证中,已经把数量+1了
}
else
list.Add(new ZhaoLing(MianE.M0_1, 1));
money(yue - 1, ref list);
}
else
{
//退出
}
}
///
/// 验证列表中是否有重复面额
///
///
///
///
private bool checkList(MianE miane,ref Listlist)
{
bool r = false;
for (int i = 0; i < list.Count; i++)
{
if (list[i].Miane == miane)
{
list[i].Count++;//发现有相同面额,直接就数量加一
r = true;
break;
}
}
return r;
}