ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

字节跳动2023年机试题

2022-08-22 17:32:27  阅读:167  来源: 互联网

标签:骰子 le 年机 字节 int mmap ++ 2023 include


T1 字节之和

双休在家的凯凯真的是太无聊了,他准备和他家的猫玩一个游戏。

凯凯随手写下一串 01 数列,定义这串数列的子串和为所有长度为2的子串的和。比如数列=010001,有如下长度为 2 的子串:
01 (前导0, =1)
10
00 (前导0,=0)
00 (前导0,=0)
01 (前导0,=1)

所以和为 1+10+0+0+1 = 12

如果要只是算子串和的话,那对喵喵来说实在是太简单了,所以凯凯准备加大难度。

喵喵有 \(k\) 次机会可以交换数列里的相邻两个数(可以不用完这 \(k\) 次机会),使得交换完之后子串和最小。

这下喵喵不会做了,你可以帮帮它么?

输入为先输入一个t,代表t组。然后分别是n、k,字符串。
input:
3
4 0
1010
7 1
0010100
5 2
00110

output:
21
22
12

对于 01 字符串,分析下它每个 1 的情况,可分为 3 种情况(中间的 \(1\) 必经过 \(1 \times 10 + 1 \times 1\)):

  1. 1 出现在字符串首部,贡献为 10
  2. 1 出现在字符串中部,贡献为 11
  3. 1 出现在字符串尾部,贡献为 1

通过以上分析可知,我们只要把 1 替换到首尾就可获得做小的和。

代码

#include <iostream>
#include <vector>
using namespace std;

int main() {
    ios::sync_with_stdio(false);

    int t;
    cin >> t;
    while (t--)
    {
        int n, k;
        cin >> n >> k;
        string s;
        cin >> s;

        int one = 0;
        for(int i = 0; i < n; i++) {
            if(s[i] == '1') one++;
        }

        if(one == 0) {
            cout << 0 << endl;
            continue;
        }

        int ans = 0;
        ans += one * 11;

        // 先将 1 尽量替换到 尾部,因为尾部的 1 贡献为 1,更小
        int rneed = 0;
        for(int i = n-1; i >=0; i--) {
            if(s[i] != '1') {
                rneed++;
            } else {
                break;
            }
        }

        // 如果 k 足够大,那么必有一个 1 贡献由 11 变为 1
        if(k >= rneed ) {
            k -= rneed;
            ans -= 10;
            // 替换后的字符串
            s[n-1] = '1';
            s[n-1-rneed] = '0';
        }

        // 替换 1 到首部,贡献由 11 减为 10
        int need = 0;
        for(int i = 0; i < n; i++) {
            if(s[i] != '1') {
                need++;
            } else {
                break;
            }
        }

        // 必有一个 1 贡献由 10 降为 1,前提是 1 不能从尾部替换到首部
        if(k >= need && (need != n-1)) {
            ans -= 1;
        }

        cout << ans << endl;
    }
}

T2 迷宫问题

第一行输入两个整数 nm ,表示迷宫的长和宽。

接下来 n 行,每行 m 个字符, 用于描述迷宫构造,每个字符可能为以下几种:

. 表示空地, 玩家在空地时可以选择往 [上,下,左,右] 中的某个方向移动一格。U,D,L,R 分别表示朝向[上,下,左,右] 的传送带,站在传送带上的人会被强制移动到其指向的下一个位置,如果下一个位置还是传送带,会被继续传下去。如果传送带指向迷宫外,玩家会撞在墙上,昏过去,游戏结束,无法再到达出口。O 表示迷宫出口

请你找到有多少点按照规则行走不能到达终点。

input:
5 5
.....
.RRD.
.U.DR
.ULL.
....O

output:
10

解这道题的思路来自于 Leetcode 417. Pacific Atlantic Water Flow 。从出口 O 反向遍历,找到所有可以从 O 反向到达的点,答案即为 \(n \times m - count(O)\) 。

出口 O 并不总是在右下角!!

#include <iostream>
#include <vector>
#include <queue>

using namespace std;

typedef pair<int, int> pii;

constexpr static int dirs[4][2] = {{-1, 0}, {1, 0}, {0, -1}, {0, 1}};

int main() {
    // freopen("bytecode002.txt", "r", stdin);
    ios::sync_with_stdio(false);
    
    int n, m;
    cin >> n >> m;

    vector<vector<char>> mmap(m, vector<char>(n));

    queue<pii> q;

    for(int i = 0; i < m; i++) {
        for(int j = 0; j < n; j++) {
            cin >> mmap[i][j];
            if(mmap[i][j] == 'O') {
                q.emplace(i, j);
            }
        }
    }

    while(!q.empty()) {
        pii cur = q.front();
        q.pop();
        int x = cur.first, y = cur.second;

        // O 处可达
        if(x-1 >= 0 && (mmap[x-1][y] == '.' || mmap[x-1][y] == 'D')) {
            q.emplace(x-1, y);
            mmap[x-1][y] = 'O';
        }

        if(x+1 < n && (mmap[x+1][y] == '.' || mmap[x+1][y] == 'U')) {
            q.emplace(x+1, y);
            mmap[x+1][y] = 'O';
        }

        if(y-1 >=0 && (mmap[x][y-1] == '.' || mmap[x][y-1] == 'R')) {
            q.emplace(x, y-1);
            mmap[x][y-1] = 'O';
        }

        if(y+1 < m && (mmap[x][y+1] == '.' || mmap[x][y+1] == 'L')) {
            q.emplace(x, y+1);
            mmap[x][y+1] = 'O';
        }
    }

    int count_O = 0;
    for(int i = 0; i < m; i++) {
        for(int j = 0; j < n; j++) {
            if(mmap[i][j] == 'O') {
                count_O++;
            }
        }
    }

    cout << n*m - count_O << endl;

}

T3 广告投放

在广告平台中,为了给广告主一定的自由性和效率,允许广告主在创造标题的时候以通配符的方式进行创意提交。线上服务的时候,会根据用户的搜索词触发的 bidword 对创意中的通配符(通配符是用成对 {} 括起来的字符串)进行替换(用0个或者多个字符替换通配符),用来提升广告投放体验。例如:{末日血战},上线送 SSR 英雄,三天集鲚无敌阵容!”,会被替换成“帝国时代下载上线送 SSR 英雄,三天集齐无敌阵容!”。给定一个含有通配符的创意和一句标题,判断这句标题是否从该创意替换生成的。

输入一个 n,有 n 个标题。第一行是带有通配符的创意,下面n行是所有标题。对于每一行标题,如果可以用通配符匹配,输出 True 否则输出 False

input:
4
ad{XYZ}cdc{Y}f{x}e
adcdcefdfeffe
adcdcefdfeff
dcdcefdfeffe
adcdcfe
 
output:
True
False
False
True

简单正则表达式处理

#include<iostream>
#include<regex>
#include<vector>

using namespace std;

int main() {
    ios::sync_with_stdio(false);

    int n;
    cin >> n;

    string tpl;
    cin >> tpl;

    vector<string> mch(n);
    for(int i = 0; i < n; i++) {
        cin >> mch[i];
    }

    regex reg("\\{[a-zA-Z]+\\}");
    string ntpl = regex_replace(tpl, reg, "\\w*");

    regex new_reg(ntpl);
    smatch m;
    for(int i = 0; i < n; i++) {
        if(regex_match(mch[i], m, new_reg)) {
            cout << "True" << endl;
        } else {
            cout << "False" << endl;
        }
    }

    return 0;
}

T4 摇骰子游戏

小明和小红在玩摇骰子游戏,每个骰子有固定的面数 \(k(2 \le k \le 8)\),每一面对应的点数分别为 \(1,2,.…,k\)。

小明有 \(n (1 \le n \le 20)\)个骰子,对于骰子 \(i (1 \le i \le n)\) ,它的面数为 \(a_i (2 \le a_i \le 8)\),摇到每一面的概率都是 \(\frac{1}{a_i}\)。

小红有 \(m (1 \le m \le 20)\) 个骰子,对于骰子 \(j(1 \le j \le m)\),它的面数为 \(b_j (2 \le bj \le 8)\),摇到每一面的概率都是 \(\frac{1}/{b_j}\)。

小明和小红分别摇各自拥有的全部骰子,然后把骰子朝上那一面的点数相加,最后比较谁的点数和最大,大的获胜,相同平手,小的获败。小明和小红只摇一把,平手不会继续重摇,小明想知道他获胜的概率,你能帮帮他吗?

输入 nm。然后输入 n 个骰子和 m 个骰子

输出获胜概率,保留小数点后 3 位。

input:
1 3
8
2 3 4

output:
0.255

标签:骰子,le,年机,字节,int,mmap,++,2023,include
来源: https://www.cnblogs.com/loganxu/p/16613273.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有