版权声明:如若转载,请联系作者。 https://blog.csdn.net/liu16659/article/details/86533713
PAT 1132
Java
1.题意
将一个偶数位的数z在中间的位置分成两个数a和b。如果 z%(a*b) =0
,那么输出 Yes
,否则输出No
2.分析
逻辑思维很简单:先求出a, 再求出b,然后判断是否能将a和b的乘积整除。
3.代码
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.StringTokenizer;
public class Main {
public static void main(String[] args) throws IOException {
Reader.init(System.in);
int n = Reader.nextInt();
int i = 0;
int num;
for (i = 0; i < n; i++) {
num = Reader.nextInt();
System.out.println(splitProduct(num));
}
// System.out.println(splitProduct(2320));
// System.out.println(splitProduct(10));
// System.out.println(splitProduct(167334));
}
public static String splitProduct(int number) {
int temp = number;
String result ="";
int a=0,b=0;
int array[] = new int[40];
int i = 0,j =0;
int index = 0;
while (temp != 0) {
array[index++] = temp % 10;
temp = temp / 10;
}
int mid = index /2;// the mid of number
i = index;
while (i >= mid) {
a = (a * 10) + array[i];
i--;
}
//System.out.println("a = "+a);
i = mid-1;
while (i >= 0 ) {
b = (b * 10) + array[i];
i--;
}
//System.out.println("b = "+b);
if (a == 0 || b == 0) {
result = "No";
}
else if (number % a == 0) {
number /= a;
if (number % b == 0) {
result = "Yes";
} else result = "No";
}
else result = "No";
return result;
}
}
class Reader {
static BufferedReader reader;
static StringTokenizer tokenizer;
/** call this method to initialize reader for InputStream */
static void init(InputStream input) throws IOException {
reader = new BufferedReader(new InputStreamReader(input) );
tokenizer = new StringTokenizer("");
//这里初始化tokenizer只是为了进入下面的while()循环,而不是别的原因。
//那么还有优化的空间么?
}
/** get next word */
static String next() throws IOException {
while ( ! tokenizer.hasMoreTokens() ) {//如果后面还有数据,则直接返回
//TODO add check for eof if necessary
tokenizer = new StringTokenizer(reader.readLine() );//否则,读取下一行
}
return tokenizer.nextToken();
}
static int nextInt() throws IOException {
return Integer.parseInt( next() );
}
static double nextDouble() throws IOException {
return Double.parseDouble( next() );
}
//获取字符 => 因为 next()方法返回的是一个String
static char nextChar() throws IOException {
return next().charAt(0);
}
}
4.执行结果
5.优化
- 去冗余语句
代码中有这么一段,是用于求出该数的左右两部分,右边的数是a,左边的数是b。
int mid = index /2;// the mid of number
i = index;
while (i >= mid) {
a = (a * 10) + array[i];
i--;
}
i = mid-1;
while (i >= 0 ) {
b = (b * 10) + array[i];
i--;
}
但是在求左右两个数的时候,这里有一个赋值操作,即i = mid - 1;
其实这一步操作是不用的,因为在第一个while
循环之后,i的值就已经是mid-1
。修改之后,再次提交,发现执行时间没有太大变化。
- 修改变量设置
因为Java中的String实在是很慢,可以用慢的惊人来形容,所以如果对于大量的测试用例来说,我觉得代码中对result的赋值操作将会发生大量的修改,这就会很浪费时间。原代码如下:
···
if (a == 0 || b == 0) {
result = "No";
}
else if (number % a == 0) {
number /= a;
if (number % b == 0) {
result = "Yes";
} else result = "No";
}
else result = "No";
return result;
···
根据以空间换时间的原则,这里不再对result进行赋值操作,而是新建两个变量,分别是
final String No = "No";
final String Yes = "Yes";
然后直接返回No
或者 Yes
。经过这个优化之后,再次提交,可以很明显的看到了执行时间的减少。
6.测试用例
3
167334
2333
12345678
1
2147483647
1
10
No