题目1:计算几何题
二维空间中给定一组点的坐标, 以任息两个点为直径绘制一个圆,求可以绘制的最大圆,满足该圆不包含其他点,输出其直径。说明,圆心0,半径r的圆包含某点P的条件是,r≥(O到P的距离)。
输入说明:第一行,点的数量,不超过200;第二行开始为点二维坐标,每个点为一行,每个点的两个维度间以空格隔开,坐标值范围为[-10000.0, 10000.0]。
输出说明:输出满足条件的圆的直径(保留小数点后3位有效数字,四舍五入)。
输入样例: 4
0 0
1 1
3 0
0 0.5
输出样例: 2.236
题目1解答:
暴力解法:遍历所有圆的半径,逐个对比找到最大值
import java.util.Scanner;
public class Main{
public static int n;
public static double[] x = new double[n + 10];
public static double[] y = new double[n + 10];
public static boolean check(double ox, double oy, double r) {
int cnt = 0;
for(int i = 1; i <= n; i++) {
double dis = Math.sqrt((x[i] - ox) * (x[i] - ox) + (y[i] - oy) * (y[i] - oy));
if(dis <= r)
cnt++;
}
if(cnt == 2)
return true;
else
return false;
}
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
n = sc.nextInt();
double ans = 0;
for(int i = 1; i <= n; i++) {
x[i] = sc.nextDouble();
y[i] = sc.nextDouble();
}
for(int i = 1; i <= n - 1; i++) {
for(int j = i + 1; j <= n; j++) {
double ox = (x[i] + x[j]) / 2;
double oy = (y[i] + y[j]) / 2;
double r = Math.sqrt((x[i] - ox) * (x[i] - ox) + (y[i] - oy) * (y[i] - oy));
if(check(ox, oy, r)) {
ans = Math.max(ans, r * 2);
}
}
}
System.out.printf("%.3f\n", ans);
}
}
题目2:动态规划题
某游戏公司设计了一个奖励活动,给N个用户(1≤N≤10^ 7)连续编号为1到N,依据用户的编号S发放奖。
发放奖励规则为:
公司随机设定三个非零正整数x,y,z。
如果S同时是x、y的倍数,奖励2张卡片;
如果S同时是y、z的倍数, 奖励4张卡片:
如果S同时是x、z的倍数,奖励8张卡片;
如果S同时是x,y, z的倍数奖励10张卡片;
其他奖励1张卡片;
以上奖励不能同时享受。满足多个奖励条件时,以最高奖励为准。
求任意连续的L个用户,使得这L个用户得到的奖励总和最多 ,输出奖励总和的值。
输入说明:第一行,输入N,L,以空格隔开; (1≤L≤N≤10^7)第二行,输入x,y,z,以空格隔开; (1≤x,y,z≤L)
输出说明:符合条件的连续L个用户的奖励总和的最大值。
输入样例: 40 7
3 5 2
输出样例: 24
题目2解答:
首先将员工编号按照游戏规则转换为获得的卡片数,用一维数组score[i]保存
然后进行动态规划三步走:
定义dp[]:dp[i]表示前i个员工获得的卡片总数
状态转移方程:ans = dp[i], i ≤ l
ans = max(ans, dp[i+ l] - dp[i]), l < i < n - l
初始值:ans = 0
import java.util.Scanner;
public class Main{
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
int l = sc.nextInt();
int x = sc.nextInt();
int y = sc.nextInt();
int z = sc.nextInt();
long[] dp = new long[n + 10];
long[] score = new long[n + 10];
dp[0] = 0;
for(int i = 1; i <= n; i++) {
int flag1, flag2, flag3, flag4;
flag1 = flag2 = flag3 = flag4 = 0;
if(i % x == 0 && i % y == 0) flag1 = 1;
if(i % y == 0 && i % z == 0) flag2 = 1;
if(i % x == 0 && i % z == 0) flag3 = 1;
if(i % x == 0 && i % y == 0 && i % z == 0) flag4 = 1;
if(flag4 == 1) score[i] = 10;
else if(flag3 == 1) score[i] = 8;
else if(flag2 == 1) score[i] = 4;
else if(flag1 == 1) score[i] = 2;
else score[i] = 1;
dp[i] = dp[i - 1] + score[i];
}
long ans = 0;
for(int i = 1; i <= n - l; i++) {
ans = Math.max(ans, dp[i + l] - dp[i]);
}
System.out.println(ans);
}
}