华为机试:解密犯罪时间

本文介绍了华为在线测试中的一道编程题——解密犯罪时间,通过两种思路解析了如何从给定数字序列中找到大于原时间的最短时间组合。首先,对数字序列进行拆分和组合,生成所有可能的分钟排列,并进行升序排序。然后,根据分钟和小时的值,判断并返回符合条件的时间。文章提供了详细的算法实现,并附有C++代码示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目描述

题目来源

在这里插入图片描述
在这里插入图片描述

题目解析

思路一

举个例子:对于[12, 24],拆成[1, 2, 4], 对列表中这三个数从小到大进行排列组合,分别是:11:11/11:12/11:21 这样子类推,然后大于 12:24 的时间便可以返回,否则返回最小的时间组合

思路二

  • 先预处理:
    • 获取可能的备选排列
    • 将字符串拆分成M和H
  • 先获取所有可能的分钟排列minList。比如说
    • 当前已有: [1, 2, 2, 4]:那么可以组成:12、12、14、21、22、24、41、42、42、44
    • 然后对上面进行升序: 12、12、14、21、22、24、41、42、42、44
  • 然后我们判断是不是改变分钟就可以得到最近的值,如果发现minList有备选值 > M,那么返回H : minList[i]
  • 如果没有,那么我们看是否可以改变小时
    • 如果H在24一下,我们使用最近的小时数
    • 遍历minList,如果发现i > H && i <=24,那么返回 i : list[0] (list[0]是能够组成的最小的分钟)
  • 否则,就是23:59,00:00,这样特殊的值:
    • 22:22
class Solution{
    std::string format(std::string HH, std::string MM){
        auto hour = HH.length() == 2 ? HH : "0"+ HH;
        auto min = MM.length() == 2 ? MM : "0" + MM;
        return hour + ":" + min;
    }
public:
    std::string process(std::string &time){
        std::string HHstr = time.substr(0, 2);
        std::string MMstr = time.substr(3, 2); // 11:22

        int HH = stoi(HHstr);
        int MM = stoi(MMstr);

        std::vector<int> nums;
        for(auto c : time){
            if(c != '.'){
                nums.push_back(c - '0');
            }
        }

        std::vector<char> list;
        for(int i : nums){
            for(int j : nums){
                if(i <= 5){
                    list.push_back(i * 10 + j);
                }
            }
        }

        std::sort(list.begin(), list.end());

        for(int i : list){
            if(i <= MM){
                continue;
            }

            return format(HHstr, std::to_string(i));
        }

        if(HH != 23){
            for(int i : list){
                if(i < HH){
                    continue;
                }
                return format(std::to_string(i) , to_string(list[0]));
            }
        }
        
        return format(to_string(list[0]), to_string(list[0]));
    }
};


int main(){
    std::string line;
    while (getline(cin, line)){
        Solution a;
        std::cout << a.process(line) << "\n";
    }
    return 0;
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值