Java를 사용하여 문자열에서 첫 번째 "요소"의 색인을 어떻게 찾을 수 있습니까?

StackOverflow https://stackoverflow.com/questions/1440748

  •  10-07-2019
  •  | 
  •  

문제

저는 Java에서 간단한 프롤로그 통역사를 작성하고 있습니다.

"List Syntax"에서 첫 번째 요소 또는 문자열의 꼬리 요소의 첫 번째 요소의 마지막 문자 색인을 어떻게 찾을 수 있습니까?

목록 구문은 다음과 같습니다.

(엑스)
(PAB)
(func (func2 a) (func3 xy))
(동등한 이브 (어머니 가인))

순서대로 각 문자열의 헤드는 다음과 같습니다.
헤드 : "x", 색인 : 1
헤드 : "P", 색인 : 1
헤드 : "func", 색인 : 4
헤드 : "동일", 색인 : 5

기본적으로, 나는 첫 번째 "(" "("공간이나 폐쇄 "로 끝나는 문자열을 일치시켜야합니다. 헤드 요소의 마지막 문자의 문자 색인이 필요합니다.

Java 에서이 색인을 일치시키고 얻으려면 어떻게해야합니까?


Brabster의 솔루션은 정말 가깝습니다. 그러나 다음을 고려하십시오.
((b x) y)

헤드 요소가 (BX) 인 경우. "("스캐너 구분자에서 "제거하여 고치려고 시도했지만"B "와"X "사이의 공간 때문에 여전히 딸꾹질이 있습니다.

유사하게 : ((((b w) x) y) z) z)

여기서 머리는 ((BW) x) y)입니다.

도움이 되었습니까?

해결책

Java 's 스캐너 클래스 (Java 1.5에서 소개)는 시작하기에 좋은 곳이 될 수 있습니다.

다음은 원하는대로 생각하는 예입니다 (Char Counting Capability를 포함하도록 업데이트).

public class Test {

    public static void main(String[] args) {

        String[] data = new String[] {
                "(X)",
                "(p a b)",
                "(func (func2 a) (func3 X Y))",
                "(equal eve (mother cain))",
                "((b X) Y)",
                "((((b W) X) Y) Z)"
        };


        for (String line:data) {
            int headIdx = 0;
            if (line.charAt(1) == '(') {
                headIdx = countBrackets(line);
            } else {
                String head = "";
                Scanner s = new Scanner(line);
                s.useDelimiter("[)|(| ]");
                head = s.next();
                headIdx = line.indexOf(head) + head.length() - 1;
            }
            System.out.println(headIdx);
        }

    }

    private static int countBrackets(String line) {
        int bracketCount = 0;
        int charCount = 0;
        for (int i = 1; i < line.length(); i++) {
            char c = line.charAt(i);
            if (c == '(') {
                bracketCount++;
            } else if (c == ')') {
                bracketCount--;
            }
            if (bracketCount == 0) {
                return charCount + 1;
            }
            charCount++;
        }
        throw new IllegalStateException("Brackets not nested properly");
    }
}

산출:

1
1
4
5
5
13

매우 우아한 솔루션은 아니지만 Regexes는 계산할 수 없습니다 (즉, 브래킷). 더 복잡한 경우 파서 생성기를 사용하는 것에 대해 생각하고 있습니다. :)

다른 팁

당신이 그것을 무력화시킬 수없는 이유가 있습니까? 이 같은?

public int firstIndex( String exp ) {
    int parenCount = 0;
    for (int i = 1; i < exp.length(); i++) {
        if (exp.charAt(i) == '(') {
            parenCount++;
        }
        else if (exp.charAt(i) == ')') {
            parenCount--;
        }
        if (parenCount == 0 && (exp.charAt(i+1) == ' ' || exp.charAt(i) == ')')) {
            return i;
        }
    }
}

나는 여기서 뭔가를 놓치고 있을지 모르지만 나는 생각한다 그것은 효과가 있습니다.

적절한 파서를 쓰는 것이 좋습니다 (연산자 우선 순위 Prolog의 경우) 및 추가 처리를위한 Java 물체의 나무로 용어를 나타냅니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top