题目描述:(百度2019实习生笔试编程题)【不知道能不能发,如果不能发的话,希望联系我删除】
题目:你是一个军团的参谋长,你现在有n个士兵(n是3的倍数)。
现在军团需要你分配你的士兵,三等分分配至AD空间,AP空间,混伤空间,这三个空间去。
每个士兵都有AD属性和AP属性,问:如何分配可以使你的战斗力总值为最高?
——————————————————————————
计算公式:
W为总战斗力,W=W1+W2+W3
W1为派往AD空间的战斗力总值,计算方式为派往AD空间的士兵的AD属性之和
W2为派往AP空间的战斗力总值,计算方式为派往AP空间的士兵的AP属性之和
W3位派往混伤空间的战斗力总值,计算方式为派往混伤空间的士兵的(AD+AP)/2之和
——————————————————————————
输入:
①第一行输入n
②第二行输入每个士兵的AD属性
③第三行输入每个士兵的AP属性
输出:
输出总战斗力W即可
——————————————————————————
测试用例:
6
1 7 3 4 5 9
2 3 9 4 3 3
测试结果:
W1=16.00=7+9
W2=11.00=2+9
W3=8.00=4+4
W=W1+W2+W3=35.00
——————————————————————————
取值范围:
3≤n<10000
1≤AD,AP≤1000
代码部分:
/*
* 正常情况下的思路:
* ①找出AD≥C的,以AD-C的值为序列,从大到小排列,选取前n/3个士兵
* ②找出AP≥C的,以AP-C的值为序列,从大到小排列,选取前n/3个士兵
* ③剩下的n/3个士兵就是混伤空间的士兵了
* 特殊情况只需将正常情况的①或者②相应更改为先计算混伤即可。
*/
import java.util.Scanner;
public class Main {
/*
* 测试用例:
6
1 7 3 4 5 9
2 3 9 4 3 3
*
*W1=16.00
*W2=11.00
*W3=8.00
*W=W1+W2+W3=35.00
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
//———————————————————————————输入部分———————————————————————————————————//
Scanner in=new Scanner(System.in);
int n=in.nextInt();//输入士兵人数,是3的倍数
double a[]=new double[n];//士兵的AD伤害
double b[]=new double[n];//士兵的AP伤害
double c[]=new double[n];//士兵的混伤
for(int i=0;i<n;i++){
a[i]=in.nextInt();//输入AD伤害
}
for(int i=0;i<n;i++){
b[i]=in.nextInt();//输入AP伤害
}
//———————————————————————————混伤计算部分—————————————————————————————————//
for(int i=0;i<n;i++){
c[i]=(double)(a[i]+b[i])/2;//计算混合伤害
System.out.printf("第%d个士兵的混伤为:%.2f ",i+1,c[i]);
System.out.println();
}
//———————————————————————————特殊情况发现部分———————————————————————————————//
///特殊情况发现器,如果都是AD>AP,或者都是AP>AD,亦或者AD>AP的个数不足n/3,亦或者AP>AD的个数不足n/3
int ADP=0;//AD大于等于AP的个数
int APD=0;//AP大于等于AD的个数
for(int i=0;i<n;i++){
if(a[i]>=b[i]){
ADP=ADP+1;
}
else if(b[i]>=a[i]){
APD=APD+1;
}
}
//———————————————————————————输出部分————————————————————————————————————//
//①正常情况:AD>=AP和AP>=AD的个数都大于等于n/3
//②特殊情况:AP>AD的个数不足n/3
//③特殊情况:AD>AP的个数不足n/3
//———————————————————————————输出部分①————————————————————————————//
if(ADP>=n/3&&APD>=n/3){//①
int xsb[]=new int [n];//已经被选择的士兵数组
/*System.out.println(xsb[0]); =0 System.out.println(xsb[1]); =0 System.out.println(xsb[2]); =0 System.out.println(xsb[3]); =0 System.out.println(xsb[4]); =0 System.out.println(xsb[5]); =0*/
xsb[0]=999;//因为初值为0,为了避免在下面判断xsb[0]=0出错,误将其判断过已经被选中,所以给xsb[0]赋值为0以外的数值
///AD空间
double W1=0.0;
int ad[]=new int [n/3];//被AD空间选中的士兵
for(int j=0;j<n/3;j++){//选AD//选出当前士兵中最适合AD的士兵
double x=0.0;
double numAD;
for(int i=0;i<n;i++){
if(xsb[i]!=i){//如果当前士兵没被选走
if(a[i]>=c[i]){//如果当前士兵适合AD空间
numAD=a[i]-c[i];
if(x==0){//x为比较器
x=numAD;
ad[j]=i;
}else if(x<numAD){
x=numAD;
ad[j]=i;
}//将当前最适合AD空间的士兵放入ad[]数组,
}
}
}
xsb[ad[j]]=ad[j];//在被选择士兵数组xsb[]中将该士兵的位置赋值为i,表示被选中了
W1=W1+a[ad[j]];//计算战斗力
System.out.printf("当前选中去AD空间的士兵为:%d",ad[j]+1);
System.out.printf(" 当前W1的值位:%.2f",W1);
System.out.println();
}
///下面的算法与上面的相同,就不过多注释了
///AP空间
double W2=0.0;
int ap[]=new int [n/3];
for(int j=0;j<n/3;j++){//选AP//选出当前士兵中最适合AP的士兵
double x=0.0;
double numAP=0.0;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
if(b[i]>=c[i]){
numAP=b[i]-c[i];
if(x==0){
x=numAP;
ap[j]=i;
}else if(x<numAP){
x=numAP;
ap[j]=i;
}
}
}
}
xsb[ap[j]]=ap[j];
W2=W2+b[ap[j]];
System.out.printf("当前选中去AP空间的士兵为:%d",ap[j]+1);
System.out.printf(" 当前W2的值位:%.2f",W2);
System.out.println();
}
///混伤空间
double W3=0.0;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
W3=W3+c[i];
System.out.printf("当前选中去混伤空间的士兵为:%d",i+1);
System.out.printf(" 当前W3的值位:%.2f",W3);
System.out.println();
}
}
System.out.printf("总战斗力W为:%.2f",W1+W2+W3);
}
//———————————————————————————输出部分②————————————————————————————//
else if(ADP<n/3){//先行计算AP,再计算混伤,再得出AD;②
int xsb[]=new int [n];//已经被选择的士兵数组
xsb[0]=999;
///AP空间
double W2=0.0;
int ap[]=new int [n/3];
for(int j=0;j<n/3;j++){//选AP//选出当前士兵中最适合AP的士兵
double x=0.0;
double numAP=0.0;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
if(b[i]>=c[i]){
numAP=b[i]-c[i];
if(x==0){
x=numAP;
ap[j]=i;
}else if(x<numAP){
x=numAP;
ap[j]=i;
}
}
}
}
xsb[ap[j]]=ap[j];
W2=W2+b[ap[j]];
System.out.printf("当前选中去AP空间的士兵为:%d",ap[j]+1);
System.out.printf(" 当前W2的值位:%.2f",W2);
System.out.println();
}
///混伤空间
double W3=0.0;
int dp[]=new int [n/3];
for(int j=0;j<n/3;j++){
double x=0.0;
double numDP=0.0;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
if(c[i]>a[i]){
numDP=c[i]-a[i];
if(x==0){
x=numDP;
dp[j]=i;
}else if (x<numDP){
x=numDP;
dp[j]=i;
}
}
}
}
xsb[dp[j]]=dp[j];
W3=W3+c[dp[j]];
System.out.printf("当前选中去混伤空间的士兵为:%d",dp[j]+1);
System.out.printf(" 当前W3的值位:%.2f",W3);
System.out.println();
}
///AD空间
double W1=0.0;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
W1=W1+a[i];
System.out.printf("当前选中去AD空间的士兵为:%d",i+1);
System.out.printf(" 当前W1的值位:%.2f",W1);
System.out.println();
}
}
System.out.printf("总战斗力W为:%.2f",W1+W2+W3);
}
//———————————————————————————输出部分③————————————————————————————//
else if(APD<n/3){//先行计算AD,再计算混伤,再得出AP;③
int xsb[]=new int [n];//已经被选择的士兵数组
xsb[0]=999;
///AD空间
double W1=0.0;
int ad[]=new int [n/3];
for(int j=0;j<n/3;j++){
double x=0.0;
double numAD;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
if(a[i]>=c[i]){
numAD=a[i]-c[i];
if(x==0){
x=numAD;
ad[j]=i;
}else if(x<numAD){
x=numAD;
ad[j]=i;
}
}
}
}
xsb[ad[j]]=ad[j];
W1=W1+a[ad[j]];
System.out.printf("当前选中去AD空间的士兵为:%d",ad[j]+1);
System.out.printf(" 当前W1的值位:%.2f",W1);
System.out.println();
}
///混伤空间
double W3=0.0;
int dp[]=new int [n/3];
for(int j=0;j<n/3;j++){
double x=0.0;
double numDP=0.0;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
if(c[i]>b[i]){
numDP=c[i]-b[i];
if(x==0){
x=numDP;
dp[j]=i;
}else if (x<numDP){
x=numDP;
dp[j]=i;
}
}
}
}
xsb[dp[j]]=dp[j];
W3=W3+c[dp[j]];
System.out.printf("当前选中去混伤空间的士兵为:%d",dp[j]+1);
System.out.printf(" 当前W3的值位:%.2f",W3);
System.out.println();
}
///AP空间
double W2=0.0;
for(int i=0;i<n;i++){
if(xsb[i]!=i){
W2=W2+b[i];
System.out.printf("当前选中去AP空间的士兵为:%d",i+1);
System.out.printf(" 当前W2的值位:%.2f",W2);
System.out.println();
}
}
System.out.printf("总战斗力W为:%.2f",W1+W2+W3);
}
in.close();
}
}
我的输入和输出结果:
6
1 7 3 4 5 9
2 3 9 4 3 3
第1个士兵的混伤为:1.50
第2个士兵的混伤为:5.00
第3个士兵的混伤为:6.00
第4个士兵的混伤为:4.00
第5个士兵的混伤为:4.00
第6个士兵的混伤为:6.00
当前选中去AD空间的士兵为:6 当前W1的值位:9.00
当前选中去AD空间的士兵为:2 当前W1的值位:16.00
当前选中去AP空间的士兵为:3 当前W2的值位:9.00
当前选中去AP空间的士兵为:1 当前W2的值位:11.00
当前选中去混伤空间的士兵为:4 当前W3的值位:4.00
当前选中去混伤空间的士兵为:5 当前W3的值位:8.00
总战斗力W为:35.00
6
2 3 4 5 5 6
1 1 3 4 3 4
第1个士兵的混伤为:1.50
第2个士兵的混伤为:2.00
第3个士兵的混伤为:3.50
第4个士兵的混伤为:4.50
第5个士兵的混伤为:4.00
第6个士兵的混伤为:5.00
当前选中去AD空间的士兵为:2 当前W1的值位:3.00
当前选中去AD空间的士兵为:5 当前W1的值位:8.00
当前选中去混伤空间的士兵为:6 当前W3的值位:5.00
当前选中去混伤空间的士兵为:1 当前W3的值位:6.50
当前选中去AP空间的士兵为:3 当前W2的值位:3.00
当前选中去AP空间的士兵为:4 当前W2的值位:7.00
总战斗力W为:21.50
6
2 1 3 5 7 3
5 2 5 9 8 4
第1个士兵的混伤为:3.50
第2个士兵的混伤为:1.50
第3个士兵的混伤为:4.00
第4个士兵的混伤为:7.00
第5个士兵的混伤为:7.50
第6个士兵的混伤为:3.50
当前选中去AP空间的士兵为:4 当前W2的值位:9.00
当前选中去AP空间的士兵为:1 当前W2的值位:14.00
当前选中去混伤空间的士兵为:3 当前W3的值位:4.00
当前选中去混伤空间的士兵为:2 当前W3的值位:5.50
当前选中去AD空间的士兵为:5 当前W1的值位:7.00
当前选中去AD空间的士兵为:6 当前W1的值位:10.00
总战斗力W为:29.50