LintCode 1674 刷题记录

1674. 倒可乐

CAT 专属题目

中文English

给定一个容积为 s 的装满可乐的瓶子和两个容积分别为 n 和 m 的空杯子, 其中 n + m = s. 问能否通过在三个容器之间来回倒可乐来平分这 s 体积的可乐? 如果可以, 返回最少倾倒可乐的次数; 反之返回 -1.

由于瓶子和杯子上没有刻度, 所以当你从一个容器倒可乐到另一个容器中时, 只能一直倒可乐直到一个容器空了或者另一个满了为止.

样例

样例 1:

输入: s = 4, n = 1, m = 3
输出: 3
解释: 
  首先, 从瓶子倒3体积的可乐到第二个杯子, 瓶子和两个杯子中分别有 1, 0, 3 体积的可乐.
  然后, 倒1体积的可乐从第二个杯子到第一个杯子, 此时三个容器分贝有 1, 1, 2 体积的可乐.
  最后, 倒1体积的可乐从第一个杯子到瓶子, 此时瓶子和第二个杯子中都有 2 体积的可乐, 平分.

样例 2:

输入: s = 7, n = 4, m = 3
输出: -1
解释: 7 体积的可乐不能被平分.

注意事项

s <= 100

public class Solution {
	    /**
	     * @param s: the volume of cola
	     * @param n: the volume of the first cup
	     * @param m: the volume of the second cup
	     * @return: the minimum number of times to be inverted
	     */
	 public int getMinTimes(int s, int n, int m) {
	     // Write your code here
	     if(s%2==1) return -1;
	     LinkedList<Integer> queue=new LinkedList<>();
	     int num=s*10000;
	     HashSet<Integer> set=new HashSet<>();
	     set.add(num);
	     queue.add(num);
	     int cnt=0;
	     while(queue.size()>0){
	         int len=queue.size();
	         cnt++;
	         while(len-->0){
	             int a=queue.poll();
	             int s1=a/10000;
	             int n1=(a/100)%100;
	             int m1=a%100;
	           //  System.out.println("cnt:"+cnt+">>>"+a);
	             
	             if(n1==s/2||m1==s/2) return cnt;
	             if(s1<s){
	                 int b=10000*Math.min(s,s1+n1)+100*Math.max(0,n1-(s-s1))+m1;
	                 if(!set.contains(b)){
	                     queue.add(b);
	                     set.add(b);
	                 }
	                 int b1=10000*Math.min(s,s1+m1)+100*n1+Math.max(0,m1-(s-s1));
	                 if(!set.contains(b1)){
	                     queue.add(b1);
	                     set.add(b1);
	                 }
	             }
	             if(n1<n){
	                 int b=10000*Math.max(0,s1-(n-n1))+100*Math.min(n,s1+n1)+m1;
	                 if(!set.contains(b)){
	                     queue.add(b);
	                     set.add(b);
	                 }
	                 int b1=10000*s1+100*Math.min(n,n1+m1)+Math.max(0,m1-(n-n1));
	                 if(!set.contains(b1)){
	                     queue.add(b1);
	                     set.add(b1);
	                 }    
	             }
	             if(m1<m){
	                 int b=10000*Math.max(0,s1-(m-m1))+100*n1+Math.min(m,m1+s1);
	                 if(!set.contains(b)){
	                     queue.add(b);
	                     set.add(b);
	                 }
	                 int b1=10000*s1+100*Math.max(0,n1-(m-m1))+Math.min(m,m1+n1);
	                 if(!set.contains(b1)){
	                     queue.add(b1);
	                     set.add(b1);
	                 }  
	             }
	         }
	     }
	     return -1;
	 }
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值