文章目录
一、网易Netease
0808C++网易云
1、竞赛题目
题目描述:有三种难度的题目分别为Easy/Medium/Hard,现在你总共有E+EM+M+MH+H道题,各个字符串的含义如下:
E表示有E道题目难度为Easy
EM表示有EM道题目难度为Easy或者Medium
M表示有M道题目难度为Medium
MH表示有MH道题目难度为Medium或者Hard
H表示有H道题目难度为Hard
你要用这些题目出尽量多的模拟赛,为了保证题目质量且含有一定的区分量,每场模拟赛需要包含Easy Medium Hard三种难度的题目各一道,求你最多能出多少场模拟赛
样例:
输入:一行五个整数,E,EM,M,MH,H,0 <= E+EM+M+MH+H <= 10^18
2 2 1 2 2
输出:输出你最多能出多少场模拟赛
3,E + EM + H,E + MH + H,EM + M + MH
思路:
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
int judge(ll E, ll EM, ll M,ll EH,ll H,ll mid) {
if (H < mid) {
EH -= (mid - H);
if(EH < 0) return 0;
}
if (E < mid) {
EM -= (mid - E);
if(EM < 0) return 0;
}
if (EM + EH + M < mid) return 0;
return 1;
}
int main() {
ll E, EM, M, EH, H, l, r, mid, ans;
cin >> E >> EM >> M >> EH >> H;
l = 0, r = (E + EM + M + EH + H);
ans = min(E, min(M, H));
while(l <= r) {
mid = (l + r) >> 1LL;
if(judge(E, EM, M, EH, H, mid)){
ans = max(ans, mid);
l = mid + 1;
}
else r = mid-1;
}
cout << ans << endl;
return 0;
}
2、分物品
题目描述:现在有n个物品,每个物品都有一个价值,现在想将这些物品分给两个人,要求这两个人分到的物品价值总和相同(个数可以不同,总价值相同即可),剩下的物品就要扔掉,现在想知道最少需要扔多少价值的物品才能满足要求分给两个人。
样例:
输入:第一行输入一个整数T,代表有T组测试数据;对于每一组测试数据,一行输入一个整数n,代表物品的个数;接下来n个数,a[i]代表每一个物品的价值1 <= T <= 10,1 <= n <= 15,1 <= a[i] <= 100000
1
5
30 60 5 15 30
输出:每一行输出最少需要扔掉多少价值的物品
20
思路:
#include <bits/stdc++.h>
using namespace std;
int n,ans,sum,a[20];
void dfs(int op,int x,int y){
if(op>=n){
if(x==y)
ans=min(ans,sum-x-y);
return;
}
dfs(op+1,x+a[op],y);
dfs(op+1,x,y+a[op]);
dfs(op+1,x,y);
}
int main(){
int T,i,j;
cin>>T;
while(T--){
cin>>n;
sum=0;
for(i=0;i<n;i++){
cin>>a[i];
sum+=a[i];
}
ans=sum;
dfs(0,0,0);
cout<<ans<<endl;
}
return 0;
}
3、最短回文
题目描述:给定一个长度为n(n<=1e3)的字符串,可以在后面加无限多的字母,问能组成的最短回文串是多长?
#include <bits/stdc++.h>
using namespace std;
bool check(string &s, int start, int end) {
int i = start, j = end;
while (i < j && s[i] == s[j]) {
++i, --j;
}
return i >= j;
}
int main() {
string s; cin >> s;
int length = s.size();
for (int i = 0; i < length; ++i) {
if (check(s, i, length - 1)) {
break;
}
}
string prefix = s.substr(0, i);
reverse(prefix.begin(), prefix.end());
cout << s + prefix << endl;
return 0;
}
4、买票
题目描述:n(n<=2000)个人排队买票,第i个人要么单独买票,要么和后面一个人一起买(反过来,就是可以和前面一个人买),单独买花费时间a[i],一起买是b[i],求所有人买完票的最短时间。开始时间是早上08:00:00 am,输出结束时间。
思路:动态规划,dp[i]表示第i个人买完票所需要的时间。对于每一个人他可以有两个选择,要么单独买票,那么需要的总的时间就是dp[i-1] + a[i],要么和前一个人一起买票,需要的总的时间就是dp[i-2] + b[i]。最后输出的时候注意格式。
#include <bits/stdc++.h>
using namespace std;
int a[2222], b[2222];
int dp[2222];
int main() {
int n; cin >> n;
for (int i = 1; i <=n; ++i) cin >> a[i];
for (int i = 2; i <= n; ++i) cin >> b[i];
memset(dp, 0, sizeof(dp));
dp[0] = 0, dp[1] = a[1];
for (int i = 2; i <= n; ++i) {
dp[i] = min(dp[i - 1] + a[i], dp[i - 2] + b[i]);
}
int hour = dp[n] / 3600 + 8;
int minutes = dp[n] % 3600 / 60;
int seconds = dp[n] % 3600 % 60;
printf("%02d:%02d:%02d ", hour, minutes, seconds);
puts(hour <= 12 ? "am" : "pm");
return 0;
}
5、教授认可
题目描述:a教授认可b教授,b教授认可c教授,那么a也认可c。现有n (小于50000)个教授,m(小于600000)个认可,可能自己认可自己,也可能重复。求互相认可的教授有多少对?
强连通分量,直接放弃。
6、素数
牛牛现在有n个正整数的数组a,牛牛可以将其中的每个数a[i]都拆成若干个和为a[i]的正整数,牛牛想知道拆后(也可以一个都不拆)这个数组最多能有多少个素数。
#include <bits/stdc++.h>
using namespace std;
int main() {
int n, d; cin >> n;
int ans = 0;
for (int i = 0; i < n; ++i) {
cin >> d;
ans += d / 2;
}
cout << ans << endl;
return 0;
}
0912C++
1、字符串搭配输出
n行,每行的字符串数量<=100,输出按照原来的顺序。
例子:3
man woman
painter teacher worker
phd
输出6行3列,用-连接
man-painter-phd
woman-painter-phd
man-teacher-phd
woman-teacher-phd
man-teacher-phd
woman-worker-phd
2、整除7
输入一个数组,输出能整除7的最大子数组和。
例子:[4 3 1 7]
输出14
3、二叉树
满二叉树是樱桃,叶子结点
4、字符串距离
0927C++
1、蛇形矩阵
第一种
#include <bits/stdc++.h>
int map[105][105];
int main() {
int C, n, m, pos, det, tot, i, j;
scanf("%d", &C);
bool flag;
while(C-- > 0) {
scanf("%d%d", &n, &m);
flag = false;
pos = 0;
tot = n * n;
det = 0;
i = j = 0;
while(pos < tot) {
if (!flag) {
// 向右
while (pos < tot && j < n - det) {
map[i][j] = pos++;
j++;
}
j--;
i++;
// 向下
while (pos < tot && i < n - det) {
map[i][j] = pos++;
i++;
}
i--;
j--;
// 向左
while (pos < tot && j >= det) {
map[i][j] = pos++;
j--;
}
// 向上
det++;
i--;
j++;
while (pos < tot && i >= det) {
map[i][j] = pos++;
i--;
}
i++;
j++;
} else {
// 向下
while (pos < tot && i < n - det) {
map[i][j] = pos++;
i++;
}
i--;
j++;
// 向右
while (pos < tot && j < n - det) {
map[i][j] = pos++;
j++;
}
j--;
i--;
// 向上
while (pos < tot && i >= det) {
map[i][j] = pos++;
i--;
}
i++;
j--;
det++;
// 向左
while (pos < tot && j >= det) {
map[i][j] = pos++;
j--;
}
j++;
i++;
}
flag = !flag;
}
while(m-- > 0) {
int x, y;
scanf("%d%d", &x, &y);
printf("%d\n", map[x][y] + 1);
}
}
return 0;
}
第二种
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
void init(vector<vector<int> >& matrix, int n) {
int left = 0, right = n - 1, up = 0, down = n - 1;
int tmp = 1;
int flag = 0;
while(1) {
if (flag == 0) { // 顺时针建图
for (int i = left; i <= right; i++) {
matrix[up][i] = tmp++;
}
if (++up > down) {
break;
}
for (int i = up; i <= down; i++) {
matrix[i][right] = tmp++;
}
if (--right < left) {
break;
}
for (int i = right; i >= left; i--) {
matrix[down][i] = tmp++;
}
if (--down < up) {
break;
}
for (int i = down; i >= up; i--) {
matrix[i][left] = tmp++;
}
if (++left > right) {
break;
}
flag = 1;
} else { // 逆时针建图
for (int i = up; i <= down; i++) {
matrix[i][left] = tmp++;
}
if (++left > right) {
break;
}
for (int i = left; i <= right; i++) {
matrix[down][i] = tmp++;
}
if (--down < up) {
break;
}
for (int i = down; i >= up; i--) {
matrix[i][right] = tmp++;
}
if (--right < left) {
break;
}
for (int i = right; i >= left; i--) {
matrix[up][i] = tmp++;
}
if (++up > down) {
break;
}
flag = 0;
}
}
}
int main() {
int c;
cin >> c;
int m, n;
int tx, ty;
while(c--) {
cin >> m >> n;
vector<vector<int> > matrix(m, vector<int>(m, 0));
init(matrix, m);
for (int i = 0; i < n; i++) {
cin >> tx >> ty;
cout << matrix[tx][ty] << endl;
}
}
return 0;
}
2、文件操作系统
第一种
#include <bits/stdc++.h>
using namespace std;
const int maxn = 1e6+5;
bool vis[maxn];
int main() {
int T, n;
scanf("%d", &T);
char op[10], filename[20];
int fd, newfd;
map<string, int> map1;
map<int, string> map2;
int curIndex;
while(T-- >0) {
map1.clear();
map2.clear();
scanf("%d", &n);
getchar();
curIndex = 0;
memset(vis, false, sizeof(vis));
for(int i = 0; i < n; i++) {
scanf("%s", op);
if(strcmp(op, "open") == 0) {
scanf("%s", filename);
// 非负整数
string name = "";
int len = strlen(filename);
for(int i = 0; i < len; i++) name += filename[i];
for(int i = curIndex; ; i++) {
if(!vis[i]) {
// 直接覆盖
map1[name] = i;
map2[i] = name;
vis[i] = true;
curIndex = i + 1;
break;
}
}
printf("%d\n", map1[name]);
} else if(strcmp(op, "dup2") == 0) {
scanf("%d %d", &fd, &newfd);
// 更改
vis[newfd] = true;
string name = map2[fd];
map1[name] = newfd;
map2[newfd] = name;
} else if(strcmp(op, "dup") == 0){
// dup,重新赋值 fd
scanf("%d", &fd);
string name = map2[fd];
for(int i = curIndex; ; i++) {
if(!vis[i]) {
// 直接覆盖
map1[name] = i;
map2[i] = name;
vis[i] = true;
break;
}
}
printf("%d\n", map1[name]);
} else if(strcmp(op, "close") == 0){
scanf("%d", &fd);
vis[fd] = false;
curIndex = min(fd, curIndex);
map2[fd] = "";
} else {
scanf("%d", &fd);
string name = map2[fd];
int siz = name.length();
for(int i = 0; i < siz; i++) {
filename[i] = name[i];
}
filename[siz] = '\0';
printf("%s\n", filename);
}
}
}
return 0;
}
第二种
#include <iostream>
#include <vector>
#include <queue>
#include <algorithm>
#include <map>
using namespace std;
void open_dup(string file, vector<string>& fes, priority_queue<int>& q, int& tmp) {
// 获取最新的tmp值
while(fes[tmp] != "*") {
tmp++;
}
// 获取最新的队顶值,如果队内的文件描述符在dup2中被操作过,需要过滤
while(!q.empty() && fes[q.top() * -1] != "*"){
q.pop();
}
if (!q.empty() ) {
fes[q.top() * -1] = file;
cout << q.top() * -1 << endl;
q.pop();
} else {
fes[tmp] = file;
cout << tmp << endl;
tmp++;
}
}
int main() {
int n;
cin >> n;
while(n--) {
int m;
cin >> m;
int tmp = 0;
priority_queue<int> q;
vector<string> files(1000005, "*");
string opt, file;
int idx, idx2;
while(m--) {
cin >> opt;
if (opt == "open") {
cin >> file;
open_dup(file, files, q, tmp);
} else if (opt == "dup") {
cin >> idx;
file = files[idx];
open_dup(file, files, q, tmp);
} else if (opt == "dup2") {
cin >> idx >> idx2;
file = files[idx];
files[idx2] = file;
} else if (opt == "close") {
cin >> idx;
if (idx < tmp) {
q.push(idx * -1);
}
files[idx] = "*";
} else if (opt == "query") {
cin >> idx;
cout << files[idx] << endl;
}
}
}
return 0;
}
3、神经网络
4、流浪地球
二、美团Meituan
1、0815技术综合-后台方向
题目忘记了,通过率不太好。
2、0313技术综合-后台方向
总共5道编程题,写了两个。
1、转置数组
给定数组行n列m,求沿对角线翻转180°的数组行m列n
(1)代码有点问题,样例正确,通过率为0
#include <bits/stdc++.h>
using namespace std;
list<int> GetNum(string str);
int main()
{
while(true)
{
string str;
//getline(cin,str);
cin>>str;
list<int> nums=GetNum(str);
nums.sort();
for(list<int> :: iterator it=nums.begin();it !=nums.end();it++)
{
cout<<*it<<endl;
}
}
system("pause");
return 0;
}
char numarr[]={'0','1','2','3','4','5','6','7','8','9'};
list<int> GetNum(string str)
{
list<int> numlist;
int startIndex=0;
while(startIndex != -1)
{
vector<char> tempnum;
startIndex=-1;
for(size_t i=0;i<str.length();i++)
{
for(size_t j=0;j<(sizeof(numarr)/sizeof(numarr[0])-1);j++)
{
if(str[i]==numarr[j])
{
startIndex=i;
break;
}
}
if(startIndex != -1)
{
tempnum.push_back(str[startIndex]);
int tempindex=0;
char tempchar=str[startIndex+(tempindex+=1)];
while(int(tempchar-48)>=0 && int (tempchar-48)<=9)
{
tempnum.push_back(tempchar);
tempchar=str[startIndex+(tempindex+=1)];
}
str.erase(startIndex,tempindex);
break;
}
}
if(!tempnum.empty())
{
numlist.push_back(stoi(string(tempnum.begin(),tempnum.end())));
}
}
return numlist;
}
(2)貌似可以
#include <bits/stdc++.h>
using namespace std;
//字符串中挑数字
void part(string _str, vector<int> &_num, vector<char> &_op)
{
int sum = 0;
unsigned int i = 0;
while (i < _str.length())
{
if ('0' <= _str.at(i) && _str.at(i) <= '9')
//还原连续的数字
sum = sum * 10 + (_str.at(i) - '0');
else
{
_num.push_back(sum);
_op.push_back(_str.at(i));
sum = 0;
}
i++;
}
//判断最后一个字符是否是数字
if (0 != sum)
_num.push_back(sum);
}
int main()
{
vector<int> num(0);
vector<char> op(0);
string str;
cin >> str;
part(str, num, op);
sort(num.begin(), num.end());
//输出测试
for (unsigned int i = 0; i < num.size(); i++)
// cout << num.at(i) << " ";
//cout << endl;
if(num.at(i)!=0)
{
cout << num.at(i) << endl;
}
for (unsigned int i = 0; i < op.size(); i++)
cout << op.at(i) << " ";
return 0;
}
2、提取字符串中的数字并按顺序排列好
三、腾讯Tencent
1、08.23后台&综合第一次笔试
1、删除链表第k个元素
2、0823技术研究和数据分析第一次笔试
1、括号有效的最少添加
题目描述:现在给你一个只包含""括号的字符串,问你至少加多少个字符是合法的,对于字符串合法的定义为:字符串为空是合法的,若字符串A合法,则字符串(A), [A]也是合法的,若字符串A和字符串B均合法,则AB合法
输入:第一行输入一个字符串s,保证只有题目要求的字符,1 <= len(s) <= 200
输出:输出最少需要添加几个字符可以构成合法的字符串
样例:输入)(][][)(
输出3
做题思路:力扣921相似题目。但是只有一种括号,这种是有多个括号,需要动态规划,来记住之前的状态。puts()函数来向窗口输出字符串。
#include <bits/stdc++.h>
using namespace std;
int dp[205][205];
int main(){
string s;
int i,j,k,p;
while(cin>>s){
memset(dp,0,sizeof(dp));
if(s.size()==1){
puts("1");
continue;
}
for(i=0;i+1<s.size();i++){
if((s[i]=='('&&s[i+1]==')')||(s[i]=='['&&s[i+1]==']'))
dp[i][i+1]=2;
}
for(i=3;i<=s.size();i++){
for(j=0;j+i-1<s.size();j++){
k=j+i-1;
dp[j][k]=max(dp[j][k],dp[j+1][k-1]);
dp[j][k]=max(dp[j][k],max(dp[j+1][k],dp[j][k-1]));
if((s[j]=='('&&s[k]==')')||(s[j]=='['&&s[k]==']')){
dp[j][k]=max(dp[j][k],dp[j+1][k-1]+2);
}
for(p=j+1;p<k;p++){
dp[j][k]=max(dp[j][k],dp[j][p]+dp[p+1][k]);
}
}
}
cout<<s.size()-dp[0][s.size()-1]<<endl;
}
return 0;
}
四、华为
0926
1、发传单
输入:
performance
Adam,125
Andy,110
Bill,92
Evan,154
organization
Aaron,Abel,Adam
Aaron,Abel,Andy
Aaron,Jone,Bill
Aaron,Jone,Evan
eof
输入的performance表示各个外包人员发的数量。organization表示经理,组员,外包。这样一种从属关系。其中一个外包人员不会被两个组员管理,一个组员不会被两个经理管理。输出这种管理层级关系,数字表示他手下的总数。要求按数字从大到小排列,如果数字一样就按名字字典序排列。
输出:
Aaron<481>
-Abel<235>
–Adam<125>
–Andy<110>
-Jone<246>
–Bill<92>
–Evan<154>
2、基因测序
3、九宫格
0930
1、螺旋矩阵
输入数组,输出螺旋矩阵
力扣54,输出螺旋矩阵一横行
class Solution {
public:
vector<int> spiralOrder(vector<vector<int>>& matrix) {
vector <int> ans;
if(matrix.empty()) return ans; //若数组为空,直接返回答案
int u = 0; //赋值上下左右边界
int d = matrix.size() - 1;
int l = 0;
int r = matrix[0].size() - 1;
while(true)
{
for(int i = l; i <= r; ++i) ans.push_back(matrix[u][i]); //向右移动直到最右
if(++ u > d) break; //重新设定上边界,若上边界大于下边界,则遍历遍历完成,下同
for(int i = u; i <= d; ++i) ans.push_back(matrix[i][r]); //向下
if(-- r < l) break; //重新设定有边界
for(int i = r; i >= l; --i) ans.push_back(matrix[d][i]); //向左
if(-- d < u) break; //重新设定下边界
for(int i = d; i >= u; --i) ans.push_back(matrix[i][l]); //向上
if(++ l > r) break; //重新设定左边界
}
return ans;
}
};
力扣59,输入一个数字输出螺旋矩阵
class Solution {
public:
vector<vector<int>> generateMatrix(int n) {
vector<vector<int>> matrix(n,vector<int>(n));
//for (int i = 0; i < matrix.size(); i++)
// matrix[i].resize(n);
// 上下左右
int u = 0;
int d = n-1;
int l = 0;
int r = n-1;
int num = 1;
while(true){
// 上
for(int i=l; i <= r; i++) matrix[u][i] = num++;
if (u++ >= d) break;
// 右
for(int i=u; i <= d; i++) matrix[i][r] = num++;
if (r-- <= l) break;
// 下
for(int i=r; i >= l; i--) matrix[d][i] = num++;
if (d-- <= u) break;
// 左
for(int i=d; i >= u; i--) matrix[i][l] = num++;
if (l++ >= r) break;
}
return matrix;
}
};
class Solution {
public:
vector<vector<int>> generateMatrix(int n) {
vector<vector<int>> res(n, vector<int>(n, 0)); // 使用vector定义一个二维数组
int startx = 0, starty = 0; // 定义每循环一个圈的起始位置
int loop = n / 2; // 每个圈循环几次,例如n为奇数3,那么loop = 1 只是循环一圈,矩阵中间的值需要单独处理
int mid = n / 2; // 矩阵中间的位置,例如:n为3, 中间的位置就是(1,1),n为5,中间位置为(2, 2)
int count = 1; // 用来给矩阵中每一个空格赋值
int offset = 1; // 每一圈循环,需要控制每一条边遍历的长度
int i,j;
while (loop --) {
i = startx;
j = starty;
// 下面开始的四个for就是模拟转了一圈
// 模拟填充上行从左到右(左闭右开)
for (j = starty; j < starty + n - offset; j++) {
res[startx][j] = count++;
}
// 模拟填充右列从上到下(左闭右开)
for (i = startx; i < startx + n - offset; i++) {
res[i][j] = count++;
}
// 模拟填充下行从右到左(左闭右开)
for (; j > starty; j--) {
res[i][j] = count++;
}
// 模拟填充左列从下到上(左闭右开)
for (; i > startx; i--) {
res[i][j] = count++;
}
// 第二圈开始的时候,起始位置要各自加1, 例如:第一圈起始位置是(0, 0),第二圈起始位置是(1, 1)
startx++;
starty++;
// offset 控制每一圈里每一条边遍历的长度
offset += 2;
}
// 如果n为奇数的话,需要单独给矩阵最中间的位置赋值
if (n % 2) {
res[mid][mid] = count;
}
return res;
}
};
做这道题,就是先把原来的矩阵拉直,再依次放到该有的位置。
#include <bits/stdc++.h>
using namespace std;
vector<int> PrintMatrix(vector<vector<int >> matrix,int columns,int rows,int start)
{
vector<int> ans;
int endX=columns-1-start;
int endY=rows-1-start;
for(int i=start;i<=endX;++i)
{
ans.push_back(matrix[start][i]);
}
if(start<endY)
{
for(int i=start+1;i<=endY;++i)
{
ans.push_back(matrix[i][endX]);
}
}
if(start<endX && start<endY)
{
for(int i=endX-1;i>=start;--i)
{
ans.push_back(matrix[endY][i]);
}
}
if(start<endX && start<endY-1)
{
for(int i=endY-1;i>=start+1;--i)
{
ans.push_back(matrix[i][start]);
}
}
return ans;
}
int main()
{
int m,n;
cin>>m>>n;
vector<vector<int > > matrix(m,vector<int>(n));
int num;
for(int i=0;i<m;++i)
{
for(int j=0;j<n;++j)
{
cin>>num;
matrix[i][j]=num;
}
}
vector<int> shuzu;
for(int i=0;i<m;++i)
{
for(int j=0;j<n;++j)
{
shuzu.push_back(matrix[i][j]);
}
}
for(int j=0;j<shuzu.size();++j)
{
cout<<shuzu[j]<<' ';
}
cout<<endl;
vector<vector<int > > res(m,vector<int>(n));
vector<int> ansss;
vector<int> temp;
int numm=0;
int st=0;
while(m>st*2 && n>st*2)
{
int endX=n-1-st;
int endY=m-1-st;
for(int i=st;i<=endX;++i)
{
res[st][i]=shuzu[numm];
++numm;
}
if(st<endY)
{
for(int i=st+1;i<=endY;++i)
{
res[i][endX]=shuzu[numm];
++numm;
}
}
if(st<endX && st<endY)
{
for(int i=endX-1;i>=st;--i)
{
res[endY][i]=(shuzu[numm]);
++numm;
}
}
if(st<endX && st<endY-1)
{
for(int i=endY-1;i>=st+1;--i)
{
res[i][st]=shuzu[numm];
++numm;
}
}
st++;
}
for(int i=0;i<m;++i)
{
for(int j=0;j<n;++j)
{
cout<<res[i][j]<<' ';
}
cout<<endl;
}
int start=0;
while(m>start*2 && n>start*2)
{
temp=PrintMatrix(matrix,n,m,start);
ansss.insert(ansss.end(),temp.begin(),temp.end());
start++;
}
for(int i=0;i<ansss.size();i++)
{
cout<<ansss[i]<<' ';
}
cout<<"end"<<endl;
return 0;
}