SMU Winter 2023 Round #14
A.解开束缚缠丝Ⅱ
题意:
给出n个字母(含大小写),求它们能构成最长回文串的长度。
思路:
找到里面成对的字符串有多少,然后如果有多出来的就+1,如果没有了就不加了,如果有三个只能算其中的两个。
代码:
点击查看代码
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int T = scanner.nextInt();
int count = 0;
while(T-->0) {
int[] arr = new int[130];
int n = scanner.nextInt();
char[] ch = new char[n];
for(int i = 0;i < n;i++) {
ch[i] = scanner.next().charAt(0);
arr[ch[i]]++;
}
count=0;
for(int i = 0;i < 130;i++) {
if(arr[i]>1&&arr[i]%2!=0) {
count+=arr[i]-1;
}else if(arr[i]>1&&arr[i]%2==0) {
count+=arr[i];
}
}
if(count==0) {
System.out.println(1);
}else if(count==n){
System.out.println(count);
}else if(count<n){
System.out.println(count+1);
}
}
}
}
B.7的意志
题意:
给出n个数,求有多少个区间的和是7777。
思路:
用两个指针表示这个区间,如果里面的数加起来为7777,计数器加1,并且后面的指针就减一,如果大于7777,后面的指针同样减1,这样会让区间里的数的和变小,如果小于7777,让前面的指针加1,让这个区间的和变大,如果后面的指针已经到数组最后,且区间和比7777小的话,就没必要继续了。
代码:
点击查看代码
import java.util.Scanner;
public class Main {
static int[] arr;
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int T = scanner.nextInt();
int count = 0;
while(T-->0) {
int n = scanner.nextInt();
count = 0;
arr = new int[n];
int sum1 = 0;
for(int i = 0;i < n;i++) {
arr[i] = scanner.nextInt();
sum1 += arr[i];
}
if(sum1<7777) {
System.out.println(0);
continue;
}
int sum = 0;
for(int i = 0,j=0;i < n;) {
if(sum<7777) {
if(j<n) {
sum += arr[j++];
}else {
break;
}
}else if(sum==7777) {
count++;
sum-=arr[i];
i++;
}else if(sum>7777) {
sum-=arr[i];
i++;
}
}
System.out.println(count);
}
}
}
F.月光奏鸣曲
题目:
给定两个大小为 N⋅N 的正方形,其中共有N⋅N个格子,每个格子有用数字来标识的颜色。
你可以对第一个正方形进行旋转操作,每次可以旋转绕中心顺时针旋转 90 度,也可以逆时针旋转 90 度。
求最小的操作次数,使得第一个正方形和第二个正方形匹配。
如果无法通过操作使得两个正方形匹配,请输出 −1。
我们定义匹配为:对于任意1≤i,j≤n,有第一个正方形 (i,j) 的颜色和第二个正方形上 (i,j) 颜色相同。
Input
输入第一行 T 表示一共有 T 组测试数据 (1≤T≤100)。
接下来一行输入一个正整数 N 表示正方形的大小 (1≤N≤20)。
接下来 2⋅N 行,每行 N 个数:
其中前 N 行表示第一个正方形的颜色。
后 N 行表示第二个正方形的颜色,其中颜色用数字标号 colori,j 表示 (1≤colori,j≤109)。
Output
输出 T 行,每行输出 ans 表示最小的操作次数,若不能通过操作使得两个正方形匹配,输出 −1。
思路:
将正方形旋转后的颜色用字符串来表示,然后与第二个正方形匹配即可,都没有匹配上就输出-1。
代码:
点击查看代码
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int T = scanner.nextInt();
while(T-->0) {
int n = scanner.nextInt();
int[][] a = new int[n][n];
int[][] b = new int[n][n];
String[] s1 = new String[n];
String[] s2 = new String[n];
String[] s3 = new String[n];
String[] s4 = new String[n];
String[] s5 = new String[n];
for(int i = 0;i < n;i++) {
s1[i] = "";
s2[i] = "";
s3[i] = "";
s4[i] = "";
s5[i] = "";
}
for(int i = 0;i < n;i++) {
for(int j = 0;j < n;j++) {
a[i][j] = scanner.nextInt();
s1[i]+=a[i][j];
}
}
for(int i = 0;i < n;i++) {
for(int j = 0;j < n;j++) {
b[i][j] = scanner.nextInt();
s5[i] += b[i][j];
}
}
for(int i = 0;i < n;i++) {
for(int j = n-1;j >=0;j--) {
s2[i] += a[j][i];
}
}
for(int i = n-1;i >= 0;i--) {
for(int j = 0;j <n;j++) {
s3[n-1-i] += a[j][i];
}
}
for(int i = n-1;i >= 0;i--) {
for(int j = n-1;j >= 0;j--) {
s4[n-1-i] += a[i][j];
}
}
int[] count = new int[4];
for(int i = 0;i < n;i++) {
if(s1[i].equals(s5[i])) {
count[0]++;
}else if(s2[i].equals(s5[i])) {
count[1]++;
}else if(s3[i].equals(s5[i])) {
count[2]++;
}else if(s4[i].equals(s5[i])) {
count[3]++;
}
}
if(count[0]==n) {
System.out.println(0);
}else if(count[1]==n||count[2]==n) {
System.out.println(1);
}else if(count[3]==n) {
System.out.println(2);
}else {
System.out.println(-1);
}
}
}
}
G.电子表校对
题目:

思路:
通过匹配的方式,将字符串转化为数字,将时间全部化成秒,得到结果后再用这种方式表示出来。
代码:
点击查看代码
import java.util.Scanner;
public class Main {
static String[] num = new String[]{" _ | ||_|"," | |"," _ _||_ "," _ _| _|"," |_| |"," _ |_ _|"," _ |_ |_|",
" _ | |"," _ |_||_|"," _ |_| _|"};
static String[][] num1 = new String[][] {
{" _ "," "," _ "," _ "," "," _ "," _ "," _ "," _ "," _ "},
{"| |"," |"," _|"," _|","|_|","|_ ","|_ "," |","|_|","|_|"},
{"|_|"," |","|_ "," _|"," |"," _|","|_|"," |","|_|"," _|"}};
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
char[][] ch = new char[3][18];
char[][] ch1 = new char[3][18];
for(int i = 0;i < 3;i++) {
String s = scanner.nextLine();
ch[i] = s.toCharArray();
}
for(int i = 0;i < 3;i++) {
String s = scanner.nextLine();
ch1[i] = s.toCharArray();
}
String t1 = "";
String t2 = "";
String[] s1 = new String[6];
String[] s2 = new String[6];
for(int i = 0;i < 6;i++) {
s1[i] = "";
s2[i] = "";
}
for(int i = 0;i < 3;i++) {
int m = 0;
for(int j = 0;j < 18;j = j+3) {
int k = j;
s1[m] += ""+ch[i][k]+ch[i][k+1]+ch[i][k+2];
m++;
}
}
for(int i = 0;i < 3;i++) {
int m = 0;
for(int j = 0;j < 18;j = j+3) {
int k = j;
s2[m] += ""+ch1[i][k]+ch1[i][k+1]+ch1[i][k+2];
m++;
}
}
for(int i = 0;i < 6;i++) {
for(int j = 0;j < 10;j++) {
if(s1[i].equals(num[j])) {
t1 += j;
}
}
}
for(int i = 0;i < 6;i++) {
for(int j = 0;j < 10;j++) {
if(s2[i].equals(num[j])) {
t2 += j;
}
}
}
int t3 = Integer.parseInt(t1);
int t4 = Integer.parseInt(t2);
int h1 = t3/10000;
int h2 = t4/10000;
int m1 = t3%10000/100;
int m2 = t4%10000/100;
int se1 = t3%100;
int se2 = t4%100;
int t5 = h1*3600+m1*60+se1;
int t6 = h2*3600+m2*60+se2;
int dif = Math.abs(t5-t6);
int h3 = dif/3600;
int m3 = dif%3600/60;
int se3 = dif%60;
String h4="",m4="",se4="";
if(h3<10) {
h4 = "0"+h3;
}else {
h4 = ""+h3;
}
if(m3<10) {
m4 = "0"+m3;
}else {
m4 = ""+m3;
}
if(se3<10) {
se4 = "0"+se3;
}else {
se4 = ""+se3;
}
String t7 = h4+m4+se4;
System.out.println(t7);
if(t3>t4) {
System.out.println("early");
for(int i = 0;i < 3;i++) {
for(int j = 0;j < 6;j++) {
System.out.print(num1[i][t7.charAt(j)-48]);
}
System.out.println();
}
}else if(t3<t4) {
System.out.println("late");
for(int i = 0;i < 3;i++) {
for(int j = 0;j < 6;j++) {
System.out.print(num1[i][t7.charAt(j)-48]);
}
System.out.println();
}
}else {
System.out.println("gang gang hao");
System.out.println(
" _ _ _ _ _ _ \r\n"
+ "| || || || || || |\r\n"
+ "|_||_||_||_||_||_|");
}
}
}
I.好想听肆宝唱歌啊
题目:
stff577 有 n 首特别喜爱的歌,他对每首歌的喜爱程度都能用一个整数来表示,且喜爱程度各不相同,喜爱程度越大,就说明他越想点这首歌。
由于 stff577 没有错过火西肆的每场直播,所以他知道他最想点的前 k 首歌都已经被人点过了,显然他不想浪费点歌的机会,所以他会选择第 k+1 首最想点的歌。
火西肆的直播马上就要开始了,而 stff577 实在太过紧张,不知道自己该点的歌是哪首,所以请你帮助他尽快找到他想点的歌。
最后输出歌名。
思路:
排序然后逆着顺序找就可以了。
代码:
点击查看代码
import java.util.Scanner;
public class Main {
static int arr[];
static String[] str;
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int n = scanner.nextInt();
arr = new int[n];
str = new String[n];
for(int i = 0;i < n;i++) {
arr[i] = scanner.nextInt();
str[i] = scanner.next();
}
int k = scanner.nextInt();
quick_sort(arr,0,n-1);
String s = str[n-k-1];
System.out.println(s);
}
public static void quick_sort(int[] q,int l,int r) {
if(l>=r) return;
int x = q[l+r>>1];
int i = l-1;
int j = r+1;
while(i<j) {
do i++;while(q[i]<x);
do j--;while(q[j]>x);
if(i<j) {
int temp = q[i];
q[i] = q[j];
q[j] = temp;
String s = str[i];
str[i] = str[j];
str[j] = s;
}
}
quick_sort(q,l,j);
quick_sort(q,j+1,r);
}
}
思路:
在 ygo 中有一张臭名昭著的怪兽卡「命运英雄 毁灭凤凰人」,ATK2500,DEF2100,每次毁灭凤凰人被破坏,他可以在下个回合从墓地复活(只要毁灭凤凰人被除外了,他就不能从墓地复活)。除外指移到除外区,是一个不同于场上、手牌和墓地的区域,从墓地复活的怪兽卡不能从除外区复活。
你希望能在这一回合中解掉毁灭凤凰人并且让他不能复活,你手上有 n 张卡牌,可能由以下卡片组成:
0 表示怪兽卡,如果对方的毁灭凤凰人是攻击表示的,那么只要这张怪兽卡的 ATK 大于等于毁灭凤凰人的 ATK 就可以将毁灭凤凰人破坏并送入墓地,如果对方的毁灭凤凰人是守备表示的,那么只要这张怪兽卡的 ATK 大于毁灭凤凰人的 DEF 就可以将毁灭凤凰人破坏并送入墓地。
1 表示「墓穴的指名者」,非怪兽卡,他可以将对方墓地一张怪兽卡除外(只能使墓地的怪兽卡除外)。
2 表示「黑核」,非怪兽卡,他可以将场上的毁灭凤凰人除外,但是必须丢弃一张其他手牌才能发动(只能除外场上的,即没有被破坏送入墓地的怪兽)。
简单来说,你要合理运用你的手牌将毁灭凤凰人除外,比如先使用怪兽卡将毁灭凤凰人破坏并送入墓地,再使用「墓穴的指名者」将毁灭凤凰人除外,或者丢弃一张手牌使用「黑核」直接将场上的毁灭凤凰人除外。
Input
第一行两个数字 n,m(0≤n≤10,0≤m≤1) 表示你的手牌数量和毁灭凤凰人的表示形式,0 表示攻击表示,1 表示守备表示。
接下来 n 行每行输入一个数字 xi(0≤xi≤2),表示第 i 张卡片的种类,如果是 0,则会再输入一个数字 k,(0≤k≤104) 表示攻击力。
Output
如果可以解掉毁灭凤凰人并使他不能复活,就在一行内输出 "haoye"(不包括引号),否则输出 "QAQ"(不包括引号)。
思路:
这里主要考虑两种情况,一是先击败,再除外;二是弃一张牌直接除外。
还有就是仔细读题,注意防御那里的判断条件与攻击那里不一样。
代码:
点击查看代码
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int n = scanner.nextInt();
int m = scanner.nextInt();
int[] arr = new int[n];
int[] arr1 = new int[n];
for(int i = 0;i < n;i++) {
arr[i] = scanner.nextInt();
if(arr[i]==0) {
arr1[i] = scanner.nextInt();
}
}
for(int i = 0;i < n-1;i++) {
if(arr[i]==0&&m==0&&arr1[i]>=2500) {
for(int j = 0;j<n;j++) {
if(arr[j]==1) {
System.out.println("haoye");
return;
}
}
}else if(arr[i]==0&&m==1&&arr1[i]>2100) {
for(int j = 0;j<n;j++) {
if(arr[j]==1) {
System.out.println("haoye");
return;
}
}
}else if(arr[i]==2&&n>=2) {
System.out.println("haoye");
return;
}
}
System.out.println("QAQ");
}
}
K. 欢迎来到杭师大
题意:
输入数字n,输出n遍Welcome to HZNU
思路:
签到题,按题目输出即可。
代码:
点击查看代码
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int n = scanner.nextInt();
for(int i = 0;i < n;i++) {
System.out.println("Welcome to HZNU");
}
}
}
L. Ayanoto 变形记
题目:
可怜的 Ayanoto 被巫师变成了一只小青蛙。
巫师把他放到圆环上的某一点,并告诉他,如果你从这里出发,并能再次到这里,就能变回人类。
圆环上有 n 个点,简便起见编号为 0 到 n−1。
由于是青蛙的体型,他每一步只能跳确切的 x 个长度。
比如说,如果他现在在 0 号点,那么下一步,他可以向前跳到第 x 个点。
请你判断,经过不断的跳跃后,Ayanoto是否有可能变为人类。
Input
t 组输入 (1≤t≤10^3)。
每组输入包含两个数字 n(2≤n≤106),x(0≤x≤106)。
Output
t 行输出,如果 Ayanoto 可以变为人类输出 "yes"(没有引号),否则输出 "no"(没有引号)。
思路:
只要步数不为0,就可以到终点。
代码:
点击查看代码
import java.util.Scanner;
public class MainL {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int T = scanner.nextInt();
while(T-->0) {
int n = scanner.nextInt();
int x = scanner.nextInt();
if(x==0) {
System.out.println("no");
}else {
System.out.println("yes");
}
}
}
}
M.P龙学长的教诲
题目:
给出a1 a3 a5⋯ a6 a4 a2 形式的字符串,以a1 a2 a3 a4 a5 a6⋯的形式输出。
思路:
找规律,是两边到中间输出
代码:
点击查看代码
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int T = scanner.nextInt();
scanner.nextLine();
while(T-->0) {
String str = scanner.nextLine();
int l = str.length();
char op = str.charAt(str.length()-1);
String[] s = new String[1000];
for(int i = 0;i < 1000;i++) {
s[i] = "";
}
int j = 0;
for(int i = 0;i < str.length();i++) {
if(str.charAt(i)==' ') {
j++;
i++;
}
if(str.charAt(i)==op) {
break;
}
s[j] += str.charAt(i);
}
if(j%2==0) {
s[j/2]+=op;
}else {
s[j/2+1]+=op;
}
for(int i = 0;i <= j/2;i++) {
System.out.print(s[i]+" ");
if(j-i>j/2)
System.out.print(s[j-i] + " ");
}
System.out.println();
}
}
}

浙公网安备 33010602011771号