Java 字符串索引超出范围 '}' 标记不正确 inluded/printing

Java String index out of range '}' token not inluded/printing properly

我目前有这段代码,除了“}”标记外都可以使用。 如果我输入

WOrd 023 {dOor "knob!"}

输出为

`WOrd 023 {dOor "knob!"}
WOrd
word
main.WordToken@33909752
023
23
main.NumberToken@55f96302
{
main.StartToken@3d4eac69
dOor
door
main.WordToken@42a57993
knob!
main.QuoteToken@75b84c92
Exception in thread "main" java.lang.StringIndexOutOfBoundsException: String index out of range: -1
at java.lang.String.substring(Unknown Source)
at main.ScannerBean.scan(ScannerBean.java:85)
at main.Assignment3.main(Assignment3.java:11)`

我很确定 startIndex 或 endIndex 有问题,但到目前为止我几乎没有做任何改进。对于其他输入,错误不会出现,但 '}' 仍然不会按应有的方式打印。我还注意到“-”和“+”标记也没有打印。原文:

package main;
public class ScannerBean implements TokenInterface, ScannerBeanInterface{
String Input;
public ScannerBean(String Input){
    this.Input = Input;
}
public String getInput(){
    return Input;
}
public void setInput(String Input){
    this.Input = Input;
}
public void scan() {
      int startIndex = 0;
      int stopIndex = 0;
      String mySubstring = "";
      boolean isQuote = false;
      while (++stopIndex < Input.length()) {
       if (startIndex >= Input.length()) {
        break;
       }
       if (Input.charAt(startIndex) == '"' || isQuote) {

        isQuote = true;

        if (stopIndex + 1 < Input.length() && Input.charAt(stopIndex + 1) == '"') {


         mySubstring = Input.substring(startIndex+1, stopIndex+1);
         isQuote = false;
         startIndex = stopIndex + 2;
         TokenInterface tt=new QuoteToken(mySubstring);
            System.out.println(tt.getInput());

            TokenInterface quoteToken = new QuoteToken(mySubstring);
            System.out.println(quoteToken.toString());
        }
       }
        else if (Character.isLetter(Input.charAt(startIndex))){
            if (!Character.isLetter(Input.charAt(stopIndex)) || Input.charAt(stopIndex) == '}'){
                mySubstring = Input.substring(startIndex, stopIndex);
                startIndex = stopIndex + 1;

                TokenInterface tt=new WordToken(mySubstring);
                System.out.println(tt.getInput());

                WordTokenInterface w = new WordToken(mySubstring);
                System.out.println(w.getValue());

                System.out.println(w.toString());

            }
        }
        else if (Character.isDigit(Input.charAt(startIndex))){
            if(!Character.isDigit(Input.charAt(stopIndex))){
                mySubstring = Input.substring(startIndex, stopIndex);
                startIndex = stopIndex + 1;

                TokenInterface tt=new NumberToken(mySubstring);
                System.out.println(tt.getInput());

                NumberTokenInterface n = new NumberToken(mySubstring);
                System.out.println(n.getValue());

                System.out.println(n.toString());

            }
        }
        else if (Input.charAt(startIndex) == '{'){
            if(Input.charAt(stopIndex) != '{') {
                mySubstring = Input.substring(startIndex, stopIndex);
                startIndex = stopIndex;

                TokenInterface tt=new StartToken(mySubstring);
                System.out.println(tt.getInput());

                TokenInterface startToken = new StartToken(mySubstring);
                System.out.println(startToken.toString());
            }
        }
        else if (Input.charAt(startIndex) == '}'){
            if(Input.charAt(stopIndex) != '}') {
                mySubstring = Input.substring(startIndex, stopIndex);
                startIndex = stopIndex;

                TokenInterface tt=new EndToken(mySubstring);
                System.out.println(tt.getInput());

                TokenInterface endToken = new EndToken(mySubstring);
                System.out.println(endToken.toString());
            }
        }
        else if (Input.charAt(startIndex) == '-'){
            if(Input.charAt(startIndex) != '-' ){
                mySubstring = Input.substring(startIndex, startIndex+1);
                startIndex = stopIndex;

                TokenInterface tt=new MinusToken(mySubstring);
                System.out.println(tt.getInput());

                TokenInterface minusToken = new MinusToken(mySubstring);
                System.out.println(minusToken.toString());
            }
        }
        else if (Input.charAt(startIndex) == '+'){
            if(Input.charAt(startIndex) != '+' ){
                mySubstring = Input.substring(startIndex,stopIndex);
                startIndex = stopIndex + 1;

                TokenInterface tt=new PlusToken(mySubstring);
                System.out.println(tt.getInput());

                TokenInterface plusToken = new PlusToken(mySubstring);
                System.out.println(plusToken.toString());
            }
        }
        else if (Input.charAt(stopIndex) == ' '){
            startIndex++;
        }
}
}
}

当你在这里得到子串时

 else if (Input.charAt(startIndex) == '}'){
        if(Input.charAt(stopIndex) != '}') {
            mySubstring = Input.substring(startIndex, stopIndex);

startIndex 大于 stopIndex。我建议使用 java.util.Scanner 重写整个内容,除非有一些你不能或不想这样做的充分理由。

您可以使用其 findWithinHorizon(Pattern, int) 方法为您完成大部分工作,前提是您提供正确的 Patterns。不过,在使用 next...() 方法时要小心 - 它们总是采用完整的标记(两边用定界符分隔),这不是你想要的,除非你更改定界符。

这是一个关于如何使用它的简单示例:

static final Pattern WORD = Pattern.compile("\G[a-zA-Z]+");
static final Pattern NUMBER = Pattern.compile("\G\d+");
static final Pattern LEFT = Pattern.compile("\G\{");
static final Pattern RIGHT = Pattern.compile("\G\}");
static final Pattern QUOTES = Pattern.compile("\G\"");
static final Pattern QUOTED_CHARS = Pattern.compile("\G[^\"]*");
static final Pattern WHITESPACE = Pattern.compile("\G\s*");

public static void main(String[] args) {

    String s = "WOrd 023 \"\"{dOor \"knob!\"}";
    Scanner sc = new Scanner(s);

    while (true) {

        sc.skip(WHITESPACE);
        if (!sc.hasNext()) {
            break;
        }

        String token;

        if ((token = sc.findWithinHorizon(WORD, 0)) != null) {
            System.out.println("word: " + token);
        } else if ((token = sc.findWithinHorizon(NUMBER, 0)) != null) {
            System.out.println("number: " + token);
        } else if ((token = sc.findWithinHorizon(LEFT, 0)) != null) {
            System.out.println("left: " + token);
        } else if ((token = sc.findWithinHorizon(RIGHT, 0)) != null) {
            System.out.println("right: " + token);
        } else if ((token = sc.findWithinHorizon(QUOTES, 0)) != null) {
            token = sc.findWithinHorizon(QUOTED_CHARS, 0);
            System.out.println("quoted: '" + token + "'");
            sc.findWithinHorizon(QUOTES, 0);
        }
    }
}

详情请看这里:

http://docs.oracle.com/javase/8/docs/api/java/util/Scanner.html

http://docs.oracle.com/javase/8/docs/api/java/util/regex/Pattern.html