在 Java 代码中获取 NZEC
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/9997539/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Getting NZEC in Java Code
提问by dark_shadow
I'm trying to solve the problem http://www.codechef.com/APRIL12/problems/DUMPLING/
我正在尝试解决问题http://www.codechef.com/APRIL12/problems/DUMPLING/
I'm getting runtime error NZEC on codechef. I searched on the Internet but did not manage to make my code succeed.
我在 codechef 上收到运行时错误 NZEC。我在互联网上搜索,但没有设法使我的代码成功。
This is my code :
这是我的代码:
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.math.BigInteger;
public class Main {
public BigInteger gcd(BigInteger a,BigInteger b){
if(b.compareTo(BigInteger.valueOf(0)) == 0)
return a;
return gcd(b,a.mod(b));
}
public static void main(String[] args) {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String str;
int t = 1;
Main obj = new Main();
try{
str = br.readLine();
t = Integer.parseInt(str);
}
catch(IOException e){
System.out.println("error");
}
for(int w = 0; w < t; w++){
BigInteger a = BigInteger.valueOf(1);
BigInteger b = BigInteger.valueOf(1);
BigInteger c = BigInteger.valueOf(1);
BigInteger d = BigInteger.valueOf(1);
BigInteger k = BigInteger.valueOf(1);
try{
str = br.readLine();
String s[] = str.split(" ");
a = new BigInteger(s[0]);
b = new BigInteger(s[1]);
c = new BigInteger(s[2]);
d = new BigInteger(s[3]);
k = new BigInteger(s[4]);
}
catch(IOException e){
System.out.println("error");
}
BigInteger g1,g2,num;
if(a.compareTo(b) < 0){
num = a;
a = b;
b = num;
}
if(c.compareTo(d) < 0){
num = c;
c = d;
d = num;
}
g1 = obj.gcd(a,b);
g2 = obj.gcd(c,d);
if(g1.compareTo(g2) < 0){
num = g1;
g1 = g2;
g2 = num;
}
BigInteger g3 = obj.gcd(g1,g2);
BigInteger l = g1.divide(g3);
l = l.multiply(g2);
BigInteger res = k.divide(l);
BigInteger fin = res.multiply(BigInteger.valueOf(2));
fin = fin.add(BigInteger.valueOf(1));
System.out.println(fin);
}
}
}
can anyone please tell me where am I doing wrong?
谁能告诉我我哪里做错了?
回答by Daniel Fischer
Barring unlikely scenarios, the only possibilities for getting a nonzero exit code with that programme that I see are
除非出现不太可能的情况,我看到的使用该程序获得非零退出代码的唯一可能性是
- division by zero, but that can't happen if the input conforms to the specifications
- unexpected input format resulting in a
NumberFormatException
- 除以零,但如果输入符合规范,则不会发生
- 意外的输入格式导致
NumberFormatException
So I'm working off the latter hypothesis. An easy way to check would be to replace the two catch(IOException e)
with catch(Exception e)
, if the input is indeed not in the format you expect, you would get a 'Wrong Answer' then (but getting a WA after the change doesn't prove the hypothesis correct).
所以我正在研究后一个假设。一个简单的方法来检查将代替两个catch(IOException e)
用catch(Exception e)
,如果输入的确不是你所期望的格式,你会得到一个“错误答案”,那么(但改变后得到一个WA并不能证明假设是正确的) .
Any additional whitespace on the first line would cause a NumberFormatException
in Integer.parseInt(str)
. Additional whitespace on any later line would cause the String[]
created by str.split(" ")
to have more than five elements, if any such occurs before the fifth number on that line, the programme would try to create BigInteger.valueOf("")
, which again causes a NumberFormatException
. So I would recommend a more robust input method, for example a java.util.Scanner
that can deal with additional whitespace without problems. The methods to use here are nextInt()
for the number of test cases and nextLong()
for the rest.
第一行的任何额外空格都会导致NumberFormatException
in Integer.parseInt(str)
。后面任何一行上的额外空格都会导致String[]
created bystr.split(" ")
有五个以上的元素,如果在该行的第五个数字之前出现任何这样的情况,程序将尝试 create BigInteger.valueOf("")
,这再次导致NumberFormatException
. 所以我会推荐一种更强大的输入法,例如java.util.Scanner
可以毫无问题地处理额外空白的 a 。这里使用的方法是nextInt()
测试用例的数量和nextLong()
其余的。
Scanner scn = new Scanner(System.in);
int t = scn.nextInt();
for(int w = 0; w < t; w++){
BigInteger a = BigInteger.valueOf(scn.nextLong());
BigInteger b = BigInteger.valueOf(scn.nextLong());
BigInteger c = BigInteger.valueOf(scn.nextLong());
BigInteger d = BigInteger.valueOf(scn.nextLong());
BigInteger k = BigInteger.valueOf(scn.nextLong());
BigInteger g1,g2,num;
...
If that change leads to an accept, the cause for the NZEC was likely an unexpected input format.
如果该更改导致接受,则 NZEC 的原因可能是意外的输入格式。
You ask
你问
can anyone please tell me where am I doing wrong ?
谁能告诉我我哪里做错了?
so I'll point out some more things that are not strictly incorrect, but bad practice/pointless.
所以我会指出更多的东西,这些东西并不是严格不正确的,而是不好的做法/毫无意义。
public BigInteger gcd(BigInteger a,BigInteger b){
if(b.compareTo(BigInteger.valueOf(0)) == 0)
return a;
return gcd(b,a.mod(b));
}
That method should be static
. It involves no state whatsoever, so having to create an object just to call it is bad.
那个方法应该是static
。它不涉及任何状态,因此必须创建一个对象来调用它是不好的。
Another point, not pertinent for small numbers like those that may appear in the problem, but relevant if you deal with large numbers, is that you made it recursive. Java usually (if ever) doesn't perform tail call optimisation, and the call stack can usually only handle a few thousand calls, so you risk a StackOverflowError
with the recursive implementation. (But since the call depth is logarithmic for the Euclidean algorithm, that only concerns larger numbers.)
另一点与问题中可能出现的小数无关,但如果您处理大数,则是相关的,是您使其递归。Java 通常(如果有的话)不执行尾调用优化,并且调用堆栈通常只能处理几千个调用,因此您可能会面临StackOverflowError
递归实现的风险。(但由于欧几里德算法的调用深度是对数的,所以这只涉及更大的数字。)
catch(IOException e){
System.out.println("error");
}
Catching an exception just to print "error" to stdout is bad. If you can't do something more meaningful to handle it, don't catch it at all.
捕获异常只是为了将“错误”打印到标准输出是不好的。如果你不能做一些更有意义的事情来处理它,就不要抓住它。
for(int w = 0; w < t; w++){
BigInteger a = BigInteger.valueOf(1);
BigInteger b = BigInteger.valueOf(1);
BigInteger c = BigInteger.valueOf(1);
BigInteger d = BigInteger.valueOf(1);
BigInteger k = BigInteger.valueOf(1);
Assigning a dummy value to the variables is pointless, they will be immediately set to their real values (or the programme should die if that fails).
为变量分配一个虚拟值是没有意义的,它们将立即被设置为它们的真实值(或者如果失败,程序就会死掉)。
try{
str = br.readLine();
String s[] = str.split(" ");
a = new BigInteger(s[0]);
b = new BigInteger(s[1]);
c = new BigInteger(s[2]);
d = new BigInteger(s[3]);
k = new BigInteger(s[4]);
}
catch(IOException e){
System.out.println("error");
}
Pointless catch
again.
又没意义catch
了。
if(a.compareTo(b) < 0){
num = a;
a = b;
b = num;
}
if(c.compareTo(d) < 0){
num = c;
c = d;
d = num;
}
I suspect you swap to avoid a mod
operation where the dividend is smaller than the divisor. There are places where such micro-optimisations are important, but this is not one of them. If you had reason to care about small things like that, there'd be much more to do. For example, the problem at hand can be solved using long
(there's one place where the algorithm would need to be adapted to avoid possible overflow), and the much faster arithmetic of that primitive type would dwarf the small gain you might get from the swap here.
我怀疑你交换是为了避免mod
红利小于除数的操作。在某些地方,这种微优化很重要,但这不是其中之一。如果你有理由关心这样的小事,还有很多事情要做。例如,手头的问题可以使用long
(有一个地方需要调整算法以避免可能的溢出)来解决,并且该原始类型的更快的算术将使您可能从这里的交换中获得的小收益相形见绌.
回答by oddRishav
NZEC means “Non zero exit code”. Its essentially saying that your program ran into some error during execution. NZEC is a runtime error.
NZEC 的意思是“非零退出代码”。它本质上是说您的程序在执行过程中遇到了一些错误。NZEC 是运行时错误。
In Java, NZEC can occur even while taking Input using Scanner like…
在 Java 中,即使在使用 Scanner 进行输入时也会发生 NZEC,例如……
import java.util.*;
import java.lang.*;
import java.io.*;
class Codechef
{
public static void main (String[] args) throws java.lang.Exception
{
Scanner sc = new Scanner(system.in);
int cases = sc.nextInt();
}
}
Exception in thread "main" java.util.NoSuchElementException
at java.util.Scanner.throwFor(Scanner.java:862)
at java.util.Scanner.next(Scanner.java:1485)
at java.util.Scanner.nextInt(Scanner.java:2117)
at java.util.Scanner.nextInt(Scanner.java:2076)
at Codechef.main(Main.java:11)
线程“main”中的异常 java.util.NoSuchElementException
在 java.util.Scanner.throwFor(Scanner.java:862)
在 java.util.Scanner.next(Scanner.java:1485)
在 java.util.Scanner.nextInt(Scanner.java:2117)
在 java.util.Scanner.nextInt(Scanner.java:2076)
在 Codechef.main(Main.java:11)
Solution:
解决方案:
- Use exception handling (Easiest Way)
- 使用异常处理(最简单的方法)
try
{
// code which you think might throw an exception or whole main class code
}
catch(Exception t){
// you got the exception.
}
Take Input from Scanner like this
int x; if(sc.hasNextInt()) x=sc.nextInt();
像这样从扫描仪获取输入
int x; if(sc.hasNextInt()) x=sc.nextInt();
I encountered this problem in CodeChef
我在 CodeChef 中遇到过这个问题
回答by doubtful
Try using BufferedReader instead of Scanner class and instead of using try-catch use throws NumberFormatException and throws IOException. This is beacuse if you use try-catch, you might get a wrong answer.
尝试使用 BufferedReader 而不是 Scanner 类,而不是使用 try-catch 使用 throws NumberFormatException 并抛出 IOException。这是因为如果您使用 try-catch,您可能会得到错误的答案。
回答by RISHABH JAIN
int takingInput = sc.nextInt();
SO, I was getting NZEC error exactly at this line of code, but to avoid this runtime error you have to verify that if scanner does contain a valid integer input value, so try replacing the above line of code with following :
所以,我正好在这行代码处收到 NZEC 错误,但是为了避免此运行时错误,您必须验证扫描仪是否包含有效的整数输入值,因此请尝试将上述代码行替换为以下代码:
int takingInput=0;
if(sc.hasNextInt()){
takingInput= sc.nextInt();
}
It worked for me!
它对我有用!