牛客网--网易2018校招编程题合集
链接:https://www.nowcoder.com/questionTerminal/32c71b52db52424c89a565e4134bfe4e
来源:牛客网
小易准备去魔法王国采购魔法神器,购买魔法神器需要使用魔法币,但是小易现在一枚魔法币都没有,但是小易有两台魔法机器可以通过投入x(x可以为0)个魔法币产生更多的魔法币。
魔法机器1:如果投入x个魔法币,魔法机器会将其变为2x+1个魔法币
魔法机器2:如果投入x个魔法币,魔法机器会将其变为2x+2个魔法币
小易采购魔法神器总共需要n个魔法币,所以小易只能通过两台魔法机器产生恰好n个魔法币,小易需要你帮他设计一个投入方案使他最后恰好拥有n个魔法币。
输入描述:
输入包括一行,包括一个正整数n(1 ≤ n ≤ 10^9),表示小易需要的魔法币数量。
输出描述:
输出一个字符串,每个字符表示该次小易选取投入的魔法机器。其中只包含字符'1'和'2'。
输入
10
输出
122
逆推。
#include
const int MAXN = 100000 + 10;
int n, cnt, num[MAXN];
int main(){
while(scanf("%d", &n) != EOF){
cnt = 0;
while(n){
if(n%2 == 1){
num[cnt++] = 1;
n = (n - 1)/2;
}else{
num[cnt++] = 2;
n = (n - 2)/2;
}
}
for(int i=cnt-1; i>=0; --i){
printf("%d", num[i] );
}
printf("\n");
}
return 0;
}
链接:https://www.nowcoder.com/questionTerminal/ef6262d0381d42ebbe22d8a8554fef01?source=relative
来源:牛客网
为了得到一个数的"相反数",我们将这个数的数字顺序颠倒,然后再加上原先的数得到"相反数"。例如,为了得到1325的"相反数",首先我们将该数的数字顺序颠倒,我们得到5231,之后再加上原先的数,我们得到5231+1325=6556.如果颠倒之后的数字有前缀零,前缀零将会被忽略。例如n = 100, 颠倒之后是1.
输入描述:
输入包括一个整数n,(1 ≤ n ≤ 10^5)
输出描述:
输出一个整数,表示n的相反数
输入
1325
输出
6556
直接法。
#include
int GetRev(int n){
int ans = 0;
while(n){
ans = 10*ans + n%10;
n /= 10;
}
return ans;
}
int main(){
int ans, n;
while(scanf("%d", &n) != EOF){
ans = n + GetRev(n);
printf("%d\n", ans );
}
return 0;
}
链接:https://www.nowcoder.com/questionTerminal/97bc02e432bb4744a9e666b6c93d4479?source=relative
来源:牛客网
输入描述:
输入包括一个字符串s,字符串s的长度length(1 ≤ length ≤ 50),s只含小写字母('a'-'z')
输出描述:
输出一个整数,表示所有碎片的平均长度,四舍五入保留两位小数。 如样例所示: s = "aaabbaaac" 所有碎片的平均长度 = (3 + 2 + 3 + 1) / 4 = 2.25
输入
aaabbaaac
输出
2.25
直接法。
#include
#include
const int MAXN = 100 + 10;
int main(){
int len, i = 0, cnt = 0, sum = 0;
char ch[MAXN];
scanf("%s", ch);
len = strlen(ch);
while(i < len){
sum += 1;
while(i + 1 < len && ch[i] == ch[i+1]){
++sum;
++i;
}
++cnt;
++i;
}
printf("%.2lf\n", (1.0 * sum / cnt) );
return 0;
}
链接:https://www.nowcoder.com/questionTerminal/f58859adc39f4edc9cd8e40ba4160339?source=relative
来源:牛客网
小易现在在0号城市,每次行动小易会从当前所在的城市走到与其相邻的一个城市,小易最多能行动L次。
如果小易到达过某个城市就视为小易游历过这个城市了,小易现在要制定好的旅游计划使他能游历最多的城市,请你帮他计算一下他最多能游历过多少个城市(注意0号城市已经游历了,游历过的城市不重复计算)。
输入描述:
输入包括两行,第一行包括两个正整数n(2 ≤ n ≤ 50)和L(1 ≤ L ≤ 100),表示城市个数和小易能行动的次数。 第二行包括n-1个整数parent[i](0 ≤ parent[i] ≤ i), 对于每个合法的i(0 ≤ i ≤ n - 2),在(i+1)号城市和parent[i]间有一条道路连接。
输出描述:
输出一个整数,表示小易最多能游历的城市数量。
输入
5 2 0 1 2 3
输出
3
树形dp,最经典的树形dp方法。
#include
#include
#include
#include
using namespace std;
const int MAXN = 55;
struct Node{
int v;
Node *next;
};
Node ed[2*MAXN], *head[MAXN];
int n, L, cnt, dp[2][MAXN][2*MAXN];
void AddEdge(int v, int u){
ed[cnt].v = v;
ed[cnt].next = head[u];
head[u] = &ed[cnt++];
}
void dfs(int fa, int cur){
Node *p;
dp[1][cur][0] = 1;
for(int i=1; i<=L; ++i){
dp[0][cur][i] = dp[1][cur][i] = 1;
}
for(p=head[cur]; p!=NULL; p=p->next){
int v = p->v;
if(v == fa){
continue;
}
dfs(cur, v);
for(int i=L; i>=0; --i){
int j = 0;
for(; j+2<=i; ++j){
dp[1][cur][i] = max(dp[1][cur][i], dp[1][cur][j] + dp[1][v][i-j-2]);
dp[0][cur][i] = max(dp[0][cur][i], dp[1][cur][j] + dp[0][v][i-j-1]);
dp[0][cur][i] = max(dp[0][cur][i], dp[1][cur][j] + dp[1][v][i-j-1]);
dp[0][cur][i] = max(dp[0][cur][i], dp[0][cur][j] + dp[1][v][i-j-2]);
}
if(j + 1 <= i){
dp[0][cur][i] = max(dp[0][cur][i], dp[1][cur][j] + dp[0][v][i-j-1]);
dp[0][cur][i] = max(dp[0][cur][i], dp[1][cur][j] + dp[1][v][i-j-1]);
}
}
}
}
int main(){
int ans, tmp;
while(scanf("%d %d", &n, &L) != EOF){
memset(dp, 0, sizeof(dp));
memset(head, 0, sizeof(head));
cnt = 0;
for(int i=1; i
链接:https://www.nowcoder.com/questionTerminal/a461395335c946c5b409e79847796cd0
来源:牛客网
牛博士给小易出了一个难题:
对数列A进行重新排列,使数列A满足所有的A[i] * A[i + 1](1 ≤ i ≤ N - 1)都是4的倍数。
小易现在需要判断一个数列是否可以重排之后满足牛博士的要求。
输入描述:
输入的第一行为数列的个数t(1 ≤ t ≤ 10), 接下来每两行描述一个数列A,第一行为数列长度n(1 ≤ n ≤ 10^5) 第二行为n个正整数A[i](1 ≤ A[i] ≤ 10^9)
输出描述:
对于每个数列输出一行表示是否可以满足牛博士要求,如果可以输出Yes,否则输出No。
输入
2 3 1 10 100 4 1 2 3 4
输出
Yes No
直接法,计算 可以被4整除的数的个数, 和不被2整除的个数,%4 个数 >= %2 mod 1 个数即可。
#include
#include
const int MAXN = 100 + 10;
int main(){
int n, t, c4, c1, TC;
scanf("%d", &TC);
while(TC--){
scanf("%d", &n);
c1 = 0; c4 = 0;
for(int i =0; i= c1 ){
printf("Yes\n");
}else{
printf("No\n");
}
}
return 0;
}
链接:https://www.nowcoder.com/questionTerminal/504ad6420b314e5bb614e1684ad46d4d?source=relative
来源:牛客网
1. 空串""是合法的括号序列
2. 如果"X"和"Y"是合法的序列,那么"XY"也是一个合法的括号序列
3. 如果"X"是一个合法的序列,那么"(X)"也是一个合法的括号序列
4. 每个合法的括号序列都可以由上面的规则生成
例如"", "()", "()()()", "(()())", "(((()))"都是合法的。
从一个字符串S中移除零个或者多个字符得到的序列称为S的子序列。
例如"abcde"的子序列有"abe","","abcde"等。
定义LCS(S,T)为字符串S和字符串T最长公共子序列的长度,即一个最长的序列W既是S的子序列也是T的子序列的长度。
小易给出一个合法的括号匹配序列s,小易希望你能找出具有以下特征的括号序列t:
1、t跟s不同,但是长度相同
2、t也是一个合法的括号匹配序列
3、LCS(s, t)是满足上述两个条件的t中最大的
因为这样的t可能存在多个,小易需要你计算出满足条件的t有多少个。
如样例所示: s = "(())()",跟字符串s长度相同的合法括号匹配序列有:
"()(())", "((()))", "()()()", "(()())",其中LCS( "(())()", "()(())" )为4,其他三个都为5,所以输出3.
输入描述:
输入包括字符串s(4 ≤ |s| ≤ 50,|s|表示字符串长度),保证s是一个合法的括号匹配序列。
输出描述:
输出一个正整数,满足条件的t的个数。
输入
(())()
输出
3
转了一个弯,其实就是判断 len-1的LCS的s,这个s可以由插入一个字符串得到。(加上判断合法性即可)
#include
#include
#include
using namespace std;
bool isLegal(string s){
int l = 0, r = 0;
for(int i=0; i l){
return false;
}
}
return true;
}
int main(){
string s;
cin >> s;
int len = s.length();
unordered_map mp;
mp[ s ] = 1;
int ans = 0;
for(int i=0; i