一个小学题目的解: 规则引擎Drools实现

本文通过使用规则引擎Drools实现了一个经典的数学问题——汽水瓶问题的解决方案。小明利用初始资金购买汽水并利用空瓶换汽水,最终最大化汽水饮用数量。文章详细介绍了Drools规则的定义及程序实现过程。
同学帮他侄儿问我一个问题:
资源:
1、小明的钱可以购买50瓶汽水。
2、老板搞促销,两个空汽水瓶子可以换一瓶汽水。

问:小明最多能喝多少瓶汽水?

开始还楞了一下, 现在的小学题目还真不简单。不过马上给出答案:
先是50瓶,然后用50个空瓶换来25瓶,喝完后用25个空瓶换12瓶再多个空瓶,
喝完后用13个空瓶换6瓶,然后是7个空瓶换3瓶,然后是4个空瓶换2瓶,
然后是2个空瓶换1瓶,最后问老板借1个空瓶,再用2个空瓶换1瓶,
剩下来那个空瓶还给老板。所以喝到50+25+12+6+3+2+1+1=100

不过最近在学习规则引擎, 自然就想到了怎么用规则引擎来实现。
我的想法是:
1: 假设汽水一元一瓶, 则小明最初由50元。
2: 如果兜里有超过一元钱, 则买一瓶汽水喝, 此时:
钱减少一元,同时拥有的空瓶增加一个。
3: 如果拥有至少两个空瓶, 则两个空瓶卖给老板, 兜里的钱加一。
根据如上想法, 有了如下Drool的实现。

java文件SodaWater.java:
  1. packageorg.drools.examples;
  2. importjava.io.InputStreamReader;
  3. importjava.io.Reader;
  4. importorg.drools.FactHandle;
  5. importorg.drools.RuleBase;
  6. importorg.drools.RuleBaseFactory;
  7. importorg.drools.StatefulSession;
  8. importorg.drools.WorkingMemory;
  9. importorg.drools.compiler.PackageBuilder;
  10. importorg.drools.rule.Package;
  11. publicclassSodaWater
  12. {
  13. publicstaticfinalvoidmain(String[]args)throwsException{
  14. finalPackageBuilderbuilder=newPackageBuilder();
  15. builder.addPackageFromDrl(newInputStreamReader(SodaWater.class.getResourceAsStream("SodaWater.drl")));
  16. finalRuleBaseruleBase=RuleBaseFactory.newRuleBase();
  17. ruleBase.addPackage(builder.getPackage());
  18. finalStatefulSessionsession=ruleBase.newStatefulSession();
  19. Customercustomer=newCustomer("XiaoMing",50);
  20. session.insert(customer);
  21. session.fireAllRules();
  22. }
  23. publicstaticclassCustomer
  24. {
  25. privateStringname;
  26. privateintmoney;
  27. privateintdrinkSum;
  28. privateintblankCup;
  29. publicCustomer(Stringname,intmoney)
  30. {
  31. this.name=name;
  32. this.money=money;
  33. this.drinkSum=0;
  34. this.blankCup=0;
  35. }
  36. publicintgetMoney()
  37. {
  38. returnmoney;
  39. }
  40. publicvoidsetMoney(intmoney)
  41. {
  42. this.money=money;
  43. }
  44. publicintgetBlankCup()
  45. {
  46. returnblankCup;
  47. }
  48. publicvoidsetBlankCup(intblankCup)
  49. {
  50. this.blankCup=blankCup;
  51. }
  52. publicintgetDrinkSum()
  53. {
  54. returndrinkSum;
  55. }
  56. publicvoidsetDrinkSum(intdrinkSum)
  57. {
  58. this.drinkSum=drinkSum;
  59. }
  60. publicStringgetName()
  61. {
  62. returnname;
  63. }
  64. publicvoidsetName(Stringname)
  65. {
  66. this.name=name;
  67. }
  68. }
  69. }
rule文件:
  1. packageorg.drools.examples
  2. dialect"mvel"
  3. importorg.drools.examples.SodaWater.Customer
  4. rule"buyasodawateranddrink"
  5. when
  6. $c:Customer(money>0,$m:money,$b:blankCup,$d:drinkSum)
  7. then
  8. $c.money=$m-1;
  9. $c.blankCup=$b+1;
  10. $c.drinkSum=$d+1;
  11. System.out.println("Customer"+$c.name+"nowbuyasodawateranddrink:money="+$c.money+"andblankCup="+$c.blankCup);
  12. update($c);
  13. end
  14. rule"saleblankcupandgetmoney"
  15. when
  16. $c:Customer(blankCup>1,$b:blankCup,$m:money)
  17. then
  18. $c.blankCup=$b-2;
  19. $c.money=$m+1;
  20. System.out.println("Customer"+$c.name+"nowsale2cupsandgetmoney:money="+$c.money+",blankCup="+$c.blankCup);
  21. update($c);
  22. end
  23. rule"finishdrink"
  24. no-looptrue
  25. dialect"java"
  26. when
  27. $c:Customer(blankCup<2,money==0)
  28. then
  29. System.out.println("Customer"+$c.getName()+"finisheddrink,anddrinknumberis"+$c.getDrinkSum()+"blankCup="+$c.getBlankCup());
  30. end


运行结果如下:
Customer XiaoMing now buy a soda water and drink: money=49 and blankCup=1
Customer XiaoMing now buy a soda water and drink: money=48 and blankCup=2
Customer XiaoMing now sale 2 cups and get money: money=49, blankCup=0
Customer XiaoMing now buy a soda water and drink: money=48 and blankCup=1
Customer XiaoMing now buy a soda water and drink: money=47 and blankCup=2

...

Customer XiaoMing now buy a soda water and drink: money=1 and blankCup=1
Customer XiaoMing now buy a soda water and drink: money=0 and blankCup=2
Customer XiaoMing now sale 2 cups and get money: money=1, blankCup=0
Customer XiaoMing now buy a soda water and drink: money=0 and blankCup=1
Customer XiaoMing finished drink, and drink number is 99 blankCup=1

不过小明最后手上还有最后一个瓶子, 计算机只能到此了。
向老板借一个瓶子换一瓶汽水,喝完在还一个空瓶子,估计就是人类智慧来。

此程序需要drools的jar包,具体可见:

http://lcllcl987.iteye.com/blog/254381



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值