【leetcode】二进制手表-经典或回溯题目

回溯,题目的本意就是找组合。返回多少种不同的组合。比如说从N个数里面找出K个数不同的组合。
回溯三步骤:
1 画出递归树,找到状态变量。
本题的状态变量有:给定的总数num,组合的初始值start,以及每种不同的组合所对应的时间,这里用pair<int,int> time接收。
因此,递归树可以写成如下:

unordered_map <int> hash{[0,1],[1,2],[2,4],[3,8],[4,1],[5,2],[6,4],[7,8],[8,16],[9,32]};
void Time(int sum, int start, pair<int,int>& time)

2 找到终止点并处理
这里当num = 0 的时候就是终止的时候。

if(num == 0){
  if(time->first >11 || time->second > 59){//按照题目要求这类数据应该剪掉,俗称剪枝
  return}
  string hour = to_string(time->first);
  string minitue = to_string(time->second);
  if(minitue.size() == 1){
  	minitue.insert(0,'0');
  	}
  res.push_back(hour + ":" + minitue);
  return;
}

3 函数主体

for(int i = start ; i < 10 ; i++){
	if(time->first >11 || time->second > 59){//按照题目要求这类数据应该剪掉,俗称剪枝
  	continue;
	pair<int,int> temp = time;//回溯时候的上一个状态
	if(i < 4){
	time->first+= hash[i];
	}
	else{
	time->second+= hash[i];
	}
	Time(num-1,start+1,time);//当前状态处理完成门进入下一层。
	time = temp;//当上面的下一层处理完毕,回溯到没有处理的状态,也就是把time打回处理之前的原形。
}

整体代码如下:

class Solution{
public:
  vector<string> res;
  unordered_map <int> hash{[0,1],[1,2],[2,4],[3,8],[4,1],[5,2],[6,4],[7,8],[8,16],[9,32]};
  void Time(int sum, int start, pair<int,int>& time){
   if(num == 0){
  	if(time->first >11 || time->second > 59){//按照题目要求这类数据应该剪掉,俗称剪枝
  	return}
  	string hour = to_string(time->first);
  	string minitue = to_string(time->second);
  	if(minitue.size() == 1){
   	minitue.insert(0,'0');
   	}
  	res.push_back(hour + ":" + minitue);
  	return;
  }
for(int i = start ; i < 10 ; i++){
 if(time->first >11 || time->second > 59){//按照题目要求这类数据应该剪掉,俗称剪枝
   continue}
   pair<int,int> temp = time;//回溯时候的上一个状态
   if(i < 4){
   time->first+= hash[i];
   }
  else{
   time->second+= hash[i];
   }
   Time(num-1,start+1,time);//当前状态处理完成门进入下一层。
   time = temp;//当上面的下一层处理完毕,回溯到没有处理的状态,也就是把time打回处理之前的原形。
}
vector<string> readBinaryWatch(int num) {
  pair<int,int> time;
  Time(num,0,time);
  return res;
  }
 };
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值