Java从文件读取字符串后填充

5

好的,我有一个读取整数的文件,文件格式如下:123456-1324563

该文件将这些数字读取为字符串,我正在尝试创建一种方法,该方法将数字读取到较少一侧的任何一侧附加数字0

例如,如果运算符左侧的数字比右侧的数字少,则会向字符串添加0,以使两个数字变得相等,并返回新的字符串。因此,我需要该方法将类似于123456789-123456的字符串转换为123456789-000123456。但它仍需要确定哪一侧更短,然后在其前面填充0,但仍返回整个字符串。

编辑:

这是我最新的版本的此方法,我使用时传递+运算符时出现ArrayIndexOutOfBoundsException,但使用-运算符时完美无误。

public String pad(String line, String operator){
    String str[] = line.split(Pattern.quote(operator));

    StringBuilder left = new StringBuilder(str[0]);
    StringBuilder right = new StringBuilder(str[1]);
    left = left.reverse();
    right = right.reverse();
    int len1 = left.length();
    int len2 = right.length();
    if(len1>len2){
        while(len1!=len2){
            right.append("0");
            len1--;
        }
    }else{
        while(len1!=len2){
            left.append("0");
            len2--;
        }
    }
    return left.reverse().toString()+operator+right.reverse().toString();
}

1
请问针对给定的示例,您能告诉所需的输出吗? - pgiitu
抱歉,关于这个问题,函数执行后的输出将使上面的字符串看起来像这样:0123456-1324563。 - CLR45
@user5448221,请像编辑一样编辑您的问题,而不是改变整个问题的意思,这样现有的答案可能会变得无意义。或者如果您有另一个问题,请再次提问。 - ashiquzzaman33
1
如果你调用 pad("123456789-123456", "+");,它会抛出 index out of bounds exception 异常,但正确的调用应该是 pad("123456789+123456", "+");。你在行中传递了带有 - 的字符串,在操作符中传递了 + - ashiquzzaman33
6个回答

4

一个简单的解决方案:

public static String pad_num(String line){
    String[] groups = line.split("-");
    String left = groups[0],
            right = groups[1];

    if(left.length() < right.length()) {
        do {
            left = '0'+left;
        } while (left.length() < right.length());
    } else if(right.length() < left.length()) {
        do {
            right = '0'+right;
        } while (right.length() < left.length());
    }

    return left+'-'+right;
}

如果您没有固定的运算符,可以将其作为参数传递:
public static String pad_num(String line, String operator){
    //prevent ArrayIndexOutOfBoundsException
    if(!line.contains(operator)) {
        return line;
    }

    //prevent PatternSyntaxException by compiling it as literal
    String[] groups = Pattern.compile(operator, Pattern.LITERAL).split(line);

    //do the same
    ...

    return left+operator+right;
}

使用String进行字符串拼接不太好,因为每次都会生成新的字符串。使用StringBuilder来进行拼接更加合适。 - ashiquzzaman33
@Zaman 这是一个简单的解决方案。如果性能很重要,那么使用 StringBuilder 更好。 - Ron C

2

使用Java 8,更简洁紧凑的版本

public  String pad_num(String line, String operator){
    String str[] = line.split(Pattern.quote(operator));
    char []buff = new char[Math.abs(str[0].length()-str[1].length())];
    Arrays.fill(buff, '0');
    if(str[0].length()>str[1].length()){            
        return String.join(operator, str[0], new StringBuilder(String.valueOf(buff)).append(str[1]));
    }else{
        return String.join(operator, new StringBuilder(String.valueOf(buff)).append(str[0]), str[1]);
    }
}

如果您没有安装Java8,请使用以下实现方法

public  String pad_num(String line, String operator){
    String str[] = line.split(Pattern.quote(operator)); 
    StringBuilder left = new StringBuilder(str[0]);
    StringBuilder right = new StringBuilder(str[1]);
    left = left.reverse();
    right = right.reverse();
    int len1 = left.length();
    int len2 = right.length();
    if(len1>len2){
        while(len1!=len2){
            right.append("0");
            len1--;
        }
    }else{
        while(len1!=len2){
            left.append("0");
            len2--;
        }
    }
    return left.reverse().toString()+operator+right.reverse().toString();

}

并将这些方法称为:

String result = pad_num("123456+1324563", "+");
String result = pad_num("123456-1324563", "-");

编辑:

ArrayIndexOutOfBoundsException的原因是方法调用时参数不匹配,例如:

pad_num("123456-1324563", "+");   // - in line and + in operator

或者

pad_num("123456+1324563", "-");   // + in line and - in operator

如果运算符是加号而不是减号,我该如何处理拆分? - CLR45
你需要在前面添加 0 而不是在后面添加(参见他的示例)。将 right.append("0") 更改为 right.insert(0, "0") - Ron C
当我传入运算符时,如果是加号,我现在遇到了这个错误:java.util.regex.PatternSyntaxException: Dangling meta character '+' near index 0 +。 - CLR45
@RonC,这个很好用,我反转了StringBuilder,所以append的性能更好。 - ashiquzzaman33
好的,我想把运算符作为字符传递进去。 - CLR45

1
你可以这样做:

public String pad_num(String line){
        String[] lines = line.split("-");
        String s1=lines[0];
        String s2=lines[1];
        StringBuilder sb = new StringBuilder();
        if(s1.length() == s2.length()){
            return line;
        }else if(s1.length() > s2.length()){
            sb.append(s1);
            sb.append("-");
            for(int i=0;i<s1.length()-s2.length();i++){
                //add zeros before s2
                sb.append("0");
            }
            sb.append(s2);
        }else{
            for(int i=0;i<s2.length()-s1.length();i++){
                //add zeros before s1
                sb.append("0");
            }
            sb.append(s1);
            sb.append("-");
            sb.append(s2);
        }
    return sb.toString();
}

1
给定的解决方案有效。这里提供了另一种使用Apache StringUtils的替代方法。
public static String pad_num(String line){
    String paddedStr = null;
    String[] numbers = StringUtils.split(line, "-");
    if(numbers == null || (numbers[0].length() == numbers[1].length())) {
        return line;
    }

    if(numbers[0].length() > numbers[1].length()) {
        paddedStr = numbers[0] + "-" + StringUtils.leftPad(numbers[1], numbers[0].length(), "0");
    } else {
        paddedStr = StringUtils.leftPad(numbers[0], numbers[1].length(), "0") + "-" + numbers[1];
    }
    return paddedStr;
}

1
在“现实生活”中(假设这不是作业),您应该使用一个库来实现此目的。例如,使用Guava's Strings.padStart(),该方法变得更加简单:
import static com.google.common.base.Strings.padStart;
/* ... */
public String pad(String line, String delim, char padding) {

    String[] tokens = line.split(delim);
    int[] lengths = new int[] {tokens[0].length(), tokens[1].length()};

    return lengths[0] > lengths[1] 
            ? tokens[0] + delim + padStart(tokens[1], lengths[0], padding)

                : lengths[0] < lengths[1]
                    ? padStart(tokens[0], lengths[1], padding) + delim + tokens[1]

                             : line;
}

一些与代码相关的测试运行。
System.out.println(pad("123456-1324563", "-", '0'));
System.out.println(pad("1324563-123456", "-", '0'));
System.out.println(pad("123456789-123456", "-", '0'));
System.out.println(pad("123456-123456", "-", '0'));

yield(产出)

0123456-1324563
1324563-0123456
123456789-000123456
123456-123456

我只是想使用这个来将非常大的数字分解成较小的部分,以此来进行加法运算。 - CLR45

1

正如其他人已经告诉你的那样,使用库来完成这个任务Guava / Apache StringUtils)。

如果您坚持要手动完成,这里有另一个示例:

String pad(String s) {
    String[] parts = s.split("-");
    int n = parts[0].length() - parts[1].length();
    return n < 0
            ? String.format("%s%s-%s", zeros(Math.abs(n)), parts[0], parts[1])
            : String.format("%s-%s%s", parts[0], zeros(Math.abs(n)), parts[1]);
}

(这里是 zeros-util...)
String zeros(int numZeros) {
    char[] chars = new char[numZeros];
    Arrays.fill(chars, '0');
    return new String(chars);
}

很简洁!但是,这段代码右侧的令牌使用尾随零而不是前导零进行填充。您需要将返回语句更改为类似于 return numZeros < 0 ? padding + s : s.substring(0, s.indexOf("-")) + "-" + padding + s.substring(s.indexOf("-") + 1); 的内容。 - Mick Mnemonic
哦,我误解了问题。在这种情况下,感谢您的澄清 :) - folkol
现在改为左填充! - folkol

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接