zoukankan      html  css  js  c++  java
  • 字节跳动 2019 春季算法实习生在线笔试

    1. 题目一

    求最少收到多少硬币,即优先用大面额的硬币找零,类似于求一个数的个位十位百位。

    #include <iostream>
    #include <stdio.h>
    
    using namespace std;
    
    int main()
    {
        int n;
        scanf("%d", &n);
    
        int change = 1024 - n;
        int a = change / 64;
        int b = (change - a * 64) / 16;
        int c = (change - a * 64 - b * 16) / 4;
        int d = (change - a * 64 - b * 16 - c * 4) / 1;
    
        cout << a+b+c+d;
        return 0;
    }
    

    2. 题目二

    先处理有连续三个字母的情况。遍历字符串,定义一个 cnt 变量,如果字符与前一个字符相同,则 cnt 增 1;若不同,cnt 置 1,继续向后遍历。若 cnt 增到 3,则当前字母应该被去除,cnt 减 1。

    再处理 AABB 的情况,思路同上。遍历字符串,定义一个 cnt 变量,如果字符与前一个字符相同,则 cnt 增 1;若不同,cnt 置 1,继续向后遍历。若 cnt 增到 2,则直接查看其后的两个字符是否相同,若相同,去除第二个 B。

    由于我们是从左向右遍历,所以第三种情况完全不用额外再处理。

    #include <iostream>
    #include <stdio.h>
    #include <string.h>
    #include <vector>
    
    using namespace std;
    void Three_Consecutive(string &s);
    void Remove_AABB(string &s);
    int main()
    {
        int n;
        scanf("%d", &n);
    
        vector<string> data(n);
    
        for (int i = 0; i < n; i++)
        {
            cin >> data[i];
        }
    
        for (int i = 0; i < n; i++)
        {
            Three_Consecutive(data[i]);
            Remove_AABB(data[i]);
            cout << data[i] << endl;
        }
    
        return 0;
    }
    
    void Remove_AABB(string &s)
    {
        int n = s.size();
        string temp;
        int same = s[0];
        int cnt = 1;
        temp.push_back(s[0]);
        for (int i = 1; i < n; i++)
        {
            int AABB_flag = 0;
            if (s[i] == same)
            {
                cnt++;
                if (cnt == 2) // 遇到两个连续的字符 AA,查看其后是否有 BB
                {
                    if (i + 2 < n && s[i+1] == s[i+2])
                    {
                        AABB_flag = 1;
                        cnt = 1;
                        same = s[i+1];
                    }
                }
            }
            else
            {
                cnt = 1;
                same = s[i];
            }
            temp.push_back(s[i]);
            if (AABB_flag)
            {
                temp.push_back(s[i+1]);
                i = i + 2; // 跳过 BB 两个字符
            }
        }
        s = temp;
    }
    
    void Three_Consecutive(string &s)
    {
        int n = s.size();
        string temp;
        int same = s[0];
        int cnt = 1;
        temp.push_back(s[0]);
        for (int i = 1; i < n; i++)
        {
            int flag = 0;
            if (s[i] == same)
            {
                cnt++;
                if (cnt == 3)
                {
                    cnt--;
                    flag = 1;
                }
            }
            else
            {
                cnt = 1;
                same = s[i];
            }
            if (!flag)  temp.push_back(s[i]);
        }
        s = temp;
    }
    

    3. 题目三

    此题与 LeetCode 135——分发糖果 类似,只不过所有的人排成了一圈。因此,我们只需要先找到得分最小的人,然后以此为起始点分别向左向右遍历求得左右序奖赏即可。

    #include <iostream>
    #include <stdio.h>
    #include <algorithm>
    #include <vector>
    
    using namespace std;
    
    int Cal_Reward(vector<int> &data)
    {
        int min_value = data[0];
        int min_index = 0;
        int n = data.size();
        for (int i = 1; i < n; i++)
        {
            if (data[i] < min_value)
            {
                min_value = data[i];
                min_index = i;
            }
        }
    
        vector<int> left_reward(n, 1);
        for (int i = min_index + 1; i != min_index; i++)
        {
            int left = i - 1;
            int right = i;
    
            if (i == n)
            {
                right = 0;
                i = 0;
                left = n - 1;
            }
    
            if (data[right] > data[left])    left_reward[right] = left_reward[left] + 1;
            if (min_index == i)   break; // 最小值为 data[0]
        }
    
        vector<int> right_reward(n, 1);
        for (int i = min_index - 1; i != min_index; i--)
        {
            int left = i;
            int right = i + 1;
    
            if (i == -1)
            {
                right = 0;
                i = n - 1;
                left = i;
            }
    
            if (data[left] > data[right])    right_reward[left] = right_reward[right] + 1;
            if (min_index == i)   break; // 最小值为 data[n-1]
        }
    
        int result = 0;
        for (int i = 0; i < n; i++)
        {
            result += max(right_reward[i], left_reward[i]);
        }
        return result;
    }
    
    int main()
    {
        int n;
        scanf("%d", &n);
    
        for (int i = 0; i < n; i++)
        {
            int num;
            scanf("%d", &num);
            vector<int> data(num, 0);
            for (int j = 0; j < num; j++)
            {
                cin >> data[j];
            }
    
            cout << Cal_Reward(data) << endl;
        }
    
        return 0;
    }
    

    4. 题目四

    此题与 今日头条 2018 AI Camp 5 月 26 日在线笔试编程题第二道——最小分割分数 相似。绳子的长度最短为 0,最长为 N 根绳子的最大值。因此采用二分搜索,如果某个长度的值可以裁剪出 M 根绳子,继续往右搜索,否则向左搜索,直到区间小于 1e-3 结束。

    #include <iostream>
    #include <stdio.h>
    #include <algorithm>
    #include <vector>
    
    using namespace std;
    
    int main()
    {
        int n = 0, m = 0;
        scanf("%d %d", &n, &m);
    
        vector<int> data(n, 0);
        int max_length = 0;
        for (int i = 0; i < n; i++)
        {
            cin >> data[i];
            max_length = max_length > data[i] ? max_length : data[i];
        }
    
        float left = 0;
        float right = max_length;
    
        float result;
        while (fabs(right - left) >= 1e-3)
        {
            float mid = left + (right - left) / 2;
    
            int num = 0;
            for (int i = 0; i < n; i++)
            {
                num += int(data[i] / mid);
            }
    
            if (num >= m)
            {
                left = mid;
                result = mid;
            }
            else
            {
                right = mid;
            }
        }
    
        printf("%.2f", result);
    
        return 0;
    }
    

    获取更多精彩,请关注「seniusen」!

  • 相关阅读:
    信息收集之Nmap
    namp ssl秘钥安全性检测
    msf测试tomcat
    MobaXterm root用户连接虚拟机时出现Access denied
    最长公共子序列C
    web 入门58-70
    oninput,onpropertychange,onchange的用法和区别
    JavaScript判断图片是否加载完成的三种方式---转
    node.js
    SPP-Net
  • 原文地址:https://www.cnblogs.com/seniusen/p/10585483.html
Copyright © 2011-2022 走看看