题解 | #比较版本号#

比较版本号

http://www.nowcoder.com/practice/2b317e02f14247a49ffdbdba315459e7

题目的主要信息:

  • 给出2个版本号version1和version2,比较它们的大小
  • 版本号是由修订号组成,修订号与修订号之间由一个"."连接
  • 修订号可能有前导0,按从左到右的顺序依次比较它们的修订号,比较修订号时,只需比较忽略任何前导零后的整数值
  • 如果版本号没有指定某个下标处的修订号,则该修订号视为0
  • 版本号中每一节可能超过int的表达范围

方法一:流输入截取

具体做法:

可以通过字符串流输入按点进行分割,将两个版本号字符串通过分割得到修订号的数组。然后同时遍历两个数组,将数组的字符串组成数字再判断数字的大小关系。

需要注意,有可能某一个版本号比另一个短,修订号更少,此时应该比较下标i与修订号数组,对于越界情况需要直接取0.

class Solution {
public:
    int compare(string version1, string version2) {
        vector<string> nums1;
        vector<string> nums2;
        istringstream sin1(version1);
        istringstream sin2(version2);
        string temp;
        while(getline(sin1, temp, '.')) //流输入分割
            nums1.push_back(temp);
        while(getline(sin2, temp, '.'))
            nums2.push_back(temp);
        for(int i = 0; i < nums1.size() || i < nums2.size(); i++){
            string s1 = i < nums1.size() ? nums1[i] : "0"; //较短的版本号取0
            string s2 = i < nums2.size() ? nums2[i] : "0";
            long long num1 = 0;
            for(int i = 0; i < s1.length(); i++) //字符串转数字
                num1 = num1 * 10 + (s1[i] - '0');
            long long num2 = 0;
            for(int i = 0; i < s2.length(); i++)
                num2 = num2 * 10 + (s2[i] - '0');
            if(num1 > num2) //比较数字大小
                return 1;
            if(num1 < num2)
                return -1;
        }
        return 0;
    }
};

复杂度分析:

  • 时间复杂度:O(max(n,m))O(max(n,m)),其中mmnn分别为两个字符串的长度,流输入相当于遍历字符串,复杂度选取较高值
  • 空间复杂度:O(max(n,m))O(max(n,m)),使用了记录分割后修订号的数组,最坏长度为二者原本字符串长度最大值

方法二:遍历直接截取

具体做法:

利用两个指针表示字符串的下标,分别遍历两个字符串,每次截取点之前的数字字符组成数字,因为int会溢出,这里采用long long记录数字,然后比较两个数字大小,根据大小关系返回1或者-1,如果全部比较完都无法比较出大小关系,则返回0.

alt

class Solution {
public:
    int compare(string version1, string version2) {
        int n1 = version1.size();
        int n2 = version2.size();
        int i = 0, j = 0;
        while(i < n1 || j < n2){//直到某个字符串结束
            long long num1 = 0;
            while(i < n1 && version1[i] != '.'){ //从下一个点前截取数字
                num1 = num1 * 10 + (version1[i] - '0');
                i++;
            }
            i++; //跳过点
            long long num2 = 0;
            while(j < n2 && version2[j] != '.'){ //从下一个点前截取数字
                num2 = num2 * 10 + (version2[j] - '0');
                j++;
            }
            j++; //跳过点
            if(num1 > num2) //比较数字大小
                return 1;
            if(num1 < num2)
                return -1;
        }
        return 0; //版本号相同
    }
};

复杂度分析:

  • 时间复杂度:O(max(n,m))O(max(n,m)),其中mmnn分别为两个字符串的长度,遍历两个字符串,复杂度选取较高值
  • 空间复杂度:O(1)O(1),无额外空间
孤帆远影碧空尽 文章被收录于专栏

牛客网各类题单题解~

全部评论

相关推荐

07-17 12:07
门头沟学院 Java
勇敢牛牛不怕困难
投递OPPO等公司7个岗位
点赞 评论 收藏
分享
06-27 12:54
已编辑
门头沟学院 Java
累了,讲讲我的大学经历吧,目前在家待业。我是一个二本院校软件工程专业。最开始选专业是觉得计算机感兴趣,所以选择了他。本人学习计算机是从大二暑假结束开始的,也就是大三开始。当时每天学习,我个人认为Java以及是我生活的一部分了,就这样持续学习了一年半,来到了大四上学期末,大概是在12月中旬,我终于找的到了一家上海中厂的实习,但我发现实习生的工作很枯燥,公司分配的活也不多,大多时间也是自己在自学。就这样我秋招末才找到实习。时间来到了3月中旬,公司说我可以转正,但是转正工资只有7000,不过很稳定,不加班,双休,因为要回学校参加答辩了,同时当时也是心高气傲,认为可以找到更好的,所以放弃了转正机会,回学校准备论文。准备论文期间就也没有投递简历。然后时间来到了5月中旬,这时春招基本也结束了,然后我开始投递简历,期间只是约到了几家下场面试。工资也只有6-7k,到现在我不知道该怎么办了。已经没有当初学习的心劲了,好累呀,但是又不知道该干什么去。在家就是打游戏,boss简历投一投。每天日重一次。26秋招都说是针对26届的人,25怎么办。我好绝望。要不要参加考公、考研、央国企这些的。有没有大佬可以帮帮我。为什么感觉别人找工作都是顺其自然的事情,我感觉自己每一步都在艰难追赶。八股文背了又忘背了又忘,我每次都花很长时间去理解他,可是现在感觉八股、项目都忘完了。真的已经没有力气再去学习了。图片是我的简历,有没有大哥可以指正一下,或者说我应该走哪条路,有点不想在找工作了。
码客明:太累了就休息一下兄弟,人生不会完蛋的
如果实习可以转正,你会不...
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务