如何解析Java源代码?

时间:2014-07-13 13:08:39

标签: java startswith

我有一个问题: 我开发微小的webapp(Java),解析,编译用户来源,运行几个管理员定义的测试并返回响应 - 用户源成功通过所有测试,编译失败或执行因时间限制而终止。所以对于编译我需要知道什么是用户代码类(public class SomeClass)。这是我的代码:

String source = task.method;
StringReader sourceReader = new StringReader(source);
BufferedReader reader = new BufferedReader(sourceReader);

String labClassName = null;
while (labClassName == null) {
    String line = reader.readLine();

    if (line.startsWith("public")) {

        Scanner classNameScanner = new Scanner(line).useDelimiter("\\s");
        classNameScanner.next();
        classNameScanner.next();
        labClassName = classNameScanner.next();
    }
}

reader.close();

至于我这是一个相当丑陋的构造,但它工作,我检索必要的类名,但我觉得还有其他更方便的方法来找到一些字符串,在几次导入后以“公共类”开头。以下是用户来源的示例之一(来源非常不同,其中一些以简单的“公共类”开头,有些以进口开头,进口数量是随机的 - 只有此代码才需要):

import java.io.IOException;
import java.io.InputStream;
import java.util.Iterator;
import java.util.NoSuchElementException;

public class ISToIteratorAdapter implements Iterator<Byte> {

    public ISToIteratorAdapter(InputStream is) {
        this.is = is;
        try {
            this.last = is.read();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    private final InputStream is;
    private int last = -1;

    @Override
    public boolean hasNext() {
        return last != -1;
    }

    @Override
    public Byte next() {
        try {
            if (last != -1) {
                int tmp = last;
                last = is.read();
                return (byte) tmp;
            } else {
                throw new NoSuchElementException();
            }
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    @Override
    public void remove() {
        throw new UnsupportedOperationException();
    }
}

1 个答案:

答案 0 :(得分:0)

如果您可以预期源文件不包含任何&#34;规避行动&#34;或者捣乱你的代码,然后

Pattern pat = Pattern.compile( "^\\s*public\\s+class\\s+(\\w+).*$" );

String line = reader.readLine();
Matcher mat = pat.matcher( line );
if( mat.matches() ){
    String classname = mat.group( 1 );
    // ...
}

会找到一个包含空格,关键字&#34; public&#34;和&#34;班&#34;和班级名称。