我正在编写一个使用游程编码压缩字符串的程序。
E.g。输入" aaabbccccddd",输出应为" a3b2c4d3"。
目前该程序没有输出。
public static void main(String[] args) {
String words1 = "aabbbcccc";
String words2 = compress(words1);
System.out.println(words2);
}
private static String compress(String w1) {
StringBuilder w2 = new StringBuilder();
int k = 0;
for (int i = 0; i < w1.length(); ) {
k++;
if(i+1>w1.length() || w1.charAt(i) != w1.charAt(i+1)) {
w2.append(w1.charAt(i));
w2.append(k);
k = 0;
}
}
return ((w2.length() > w1.length())? w1: w2.toString());
}
输出在IntelliJ中没有显示任何内容,我无法弄清楚原因!也试过没有StringBuilder
。甚至在没有StringBuilder
的情况下进行了尝试,并将返回类型更改为void
,以防处理String
时出现问题。相同,没有结果。
答案 0 :(得分:3)
你遗忘的一件事是你的for循环i++
。这会导致无限循环。
除此之外,您的循环条件存在问题。 i<w1.length()-1
应该IndexOutOfBoundsException
以避免由w1.charAt(i+1)
引起的String
。
更改后,您会看到private static String compress(String w1) {
StringBuilder w2 = new StringBuilder();
int k =0;
for (int i=0; i < w1.length()-1; i++) {
k++;
if (w1.charAt(i) != w1.charAt(i+1)) {
w2.append(w1.charAt(i));
w2.append(k);
k=0;
}
}
w2.append (w1.charAt (w1.length ()-1));
w2.append (k+1);
return ((w2.length() > w1.length())? w1: w2.toString());
}
的最后一个字符未被处理。你可以在循环外处理它。
a3b2c4d3
此输出
aaabbccccddd
输入
if
编辑:
正如David正确评论的那样,你确实有代码来处理循环中的最后一个字符。您只是在private static String compress(String w1) {
StringBuilder w2 = new StringBuilder();
int k =0;
for (int i=0; i < w1.length(); i++) {
k++;
if (i+1 >= w1.length() || w1.charAt(i) != w1.charAt(i+1)) {
w2.append(w1.charAt(i));
w2.append(k);
k=0;
}
}
return ((w2.length() > w1.length())? w1: w2.toString());
}
语句中进行了错误的范围检查。
以下修复了所有问题,无需单独处理最后一个字符:
-dontwarn okio.**
-dontwarn javax.annotation.**
-dontwarn retrofit2.Platform$Java8
答案 1 :(得分:1)
正如伊兰所说,你忘记了i++
部分。此外,i+1>w1.length()
应为i+1>=w1.length()
。它应该适用于这两个变化。
private static String compress(String w1) {
StringBuilder w2 = new StringBuilder();
int k = 0;
for (int i = 0; i < w1.length(); i++) {
k++;
if(i+1>=w1.length() || w1.charAt(i) != w1.charAt(i+1)) {
w2.append(w1.charAt(i));
w2.append(k);
k = 0;
}
}
return ((w2.length() > w1.length())? w1: w2.toString());
}