[英]auto-compile, auto-run, auto-compare result in Java
dear all, i am new in Java and at now i am trying to develop an application under Java to do such these things: assumption: there is a file contains source code in Java. 亲爱的所有人,我是Java的新手,现在我正尝试在Java下开发应用程序来执行以下操作:假设:存在一个包含Java源代码的文件。 let's assume that the file contains a main class (and it's main method with several additional methods) and some inner classes which will be used during the main class running time. 我们假设该文件包含一个主类(以及它的main方法和几个其他方法)和一些内部类,这些类将在main类运行时使用。
processes: 进程:
can java do thing above? Java可以做上面的事情吗? any suggestion what should i do? 有什么建议我该怎么办?
regards, 问候,
Is this supposed to be a grading system for a programming contest or for exercises in a university course? 这应该是编程竞赛或大学课程练习的评分系统吗? There might exist open-source systems for that, so google it first if you haven't already. 可能存在为此的开源系统,所以如果您还没有Google,请先在Google上搜索它。 If you have to / want to make one yourself, I'm not sure if Java lets you limit the time spent by a program (but you could, of course, simply kill the program after waiting a certain amount of time), but the memory limit of a java program can be specified with eg -Xmx32m
when starting the program with the java
command. 如果您必须/想要自己做一个,我不确定Java是否可以限制您花费在程序上的时间(但是,您当然可以在等待一定时间后直接终止该程序),但是使用java
命令启动程序时,可以使用-Xmx32m
指定Java程序的内存限制。 If this is on a unix system, the simplest solution will probably be to use ulimit
to limit both the memory usage and the run time. 如果在UNIX系统上,则最简单的解决方案可能是使用ulimit
来限制内存使用量和运行时间。
In either case, I think you'll have to use Runtime.exec() to launch both the compiler and the program. 无论哪种情况,我都认为您必须使用Runtime.exec()来启动编译器和程序。 This will also let you feed input into the process and read the output from the process (although I/O redirection could also be performed to/from files if you launch the program with eg 这也可以让您将输入输入到进程中,并从进程中读取输出(尽管如果您使用以下命令启动程序,也可以执行I / O重定向到文件或从文件重定向)。
Runtime.getRuntime().exec("java -Xmx32m Program.class < input.txt > output.txt");
As for the comparison: unless you require an exact match (even in whitespace), the simplest solution is probably to redirect the output to a file and invoke diff
with either -b
or -w
, and possibly --ignore-blank-lines
; 至于比较:除非您需要完全匹配(即使在空格中),否则最简单的解决方案可能是将输出重定向到文件并使用-b
或-w
以及--ignore-blank-lines
调用diff
; if the return code is 0, the output is equal to the solution (except for whitespace differences). 如果返回码为0,则输出等于解决方案(空格差除外)。 On the other hand, if you need interactive grading (the program is supposed to "converse" with the grader) or if the output may be formed in different ways such that there is no unique correct answer, you can't use diff
; 另一方面,如果您需要交互式评分(该程序应该与评分器“对话”),或者如果输出可能以不同的方式形成,从而没有唯一的正确答案,则不能使用diff
。 the grader must read the process' output stream instead. 评分员必须改为读取流程的输出流。
I'd do this in shell script rather than java. 我会在Shell脚本而不是Java中执行此操作。 Would that be an option? 这是一个选择吗?
You can do the memory and time limiting using ulimit. 您可以使用ulimit进行内存和时间限制。 If you write a small shell script that does this: 如果您编写一个执行此操作的小shell脚本:
set -e
ulimit -v 32768 # ulimit -v works in 1 kB blocks, so this is 32 MB
ulimit -t 2 # ulimit -t works in seconds
java ProgramUnderTest >output
Then when you run it, it will give itself memory and time limits, and launch java as a subprocess. 然后,当您运行它时,它将给自己分配内存和时间限制,并将java作为子进程启动。 If the program completes in time (note that the limit is on CPU time, not real time), it will finish with exit status 0; 如果程序及时完成(请注意,限制是对CPU时间的限制,而不是实时的),则它将以退出状态0结束; otherwise, it will have some nonzero exit status. 否则,它将具有一些非零的退出状态。
If you want to record how much actual time was used within the limit, run java under time : 如果要记录在限制内使用了多少实际时间,请在time下运行java:
time java ProgramUnderTest >output
That will print the total amount of time used after the output. 这将打印输出后使用的总时间。
Compiling the code from a script is also easy, of course - just run javac. 当然,从脚本编译代码也很容易-只需运行javac。 Remember to check the exit status to see if the code compiled correctly. 切记检查退出状态以查看代码是否正确编译。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.