I was trying to convert the String to int. However, its encounter error throw a NumberFormatException.
java.lang.NumberFormatException: For input string: "07221255201"
Code :
int value = Integer.valueOf(itemData.get(row).ERP_Customer_Item.trim());
Kindly advise.
7221255201 is out of primitive int range. You should use long type.
This should work fine:
long value = Long.parseLong(itemData.get(row).ERP_Customer_Item.trim());
And for other contexts, try to have a practice of keeping primitive type ranges in mind when you write code. It is like having a hammer set consisting of hammers of different size and using the appropriate one in the context. For example, if you know that a particular variable will always be in the range of [-128,127] you should use short instead of int since you will waste a lot of bits in the latter case.
Your number is larger than Integer.MAX_VALUE (2^31 - 1, or 2147483647), so it can't be parsed into an int.
Be careful converting from strings to numbers. Whatever created that number wasn't using java ints.
You can use a Long.parseLong to convert to a long, or Long.valueOf to get a Long (object instead of primative) in this case, but why are you converting from string in the first place? You're losing information (in this case the leading zeros which may or may not be important depending on what you do with the data). Conversion has a way of biting back somewhere down the line.
Related
This question already has answers here:
Why is the default type of Java integer literals int instead of long? [closed]
(7 answers)
Closed 6 months ago.
I know that max value for int and long are very high but somehow I am not able to handle them in my code. I am getting compilation error in all the scenarios below. Could someone please suggest how I can handle 20118998631 value.
I know that if I put l after this value 20118998631l then declaring it as long will work but problem is that I am getting this from a network call and if I declare my field as long and value will come simply as 20118998631 then it will break.
int x = 20118998631; // compilation error
long l = 20118998631; // compilation error
double d = 20118998631; // compilation error
Long l1 = new Long(20118998631); // compilation error
I know that max value for int and long are very high
The definition of 'very' is in the eye of the beholder, isn't it?
The max value of an int is Integer.MAX_VALUE, which is 2147483647. Specifically, that's 2, to the 31st power, minus 1. Because computers use bits, int uses 32 bits, and about half of all the numbers an int can represent are used to represent negative numbers, hence why you end up with 2^31-1 as max int.
For longs, its 2^63-1 for the same reason: long uses 64 bit, and half of all representable values are negative.
If you have numbers that are larger than this, you need to use BigInteger (a class in the standard library for integers of arbitrary size) or byte[] or something else.
but problem is that I am getting this from a network call and if I declare my field as long and value will come simply as 20118998631 then it will break.
This doesn't make sense. Are you getting stuff from the network, shoving what you get into a file with a prefix and suffix, and then that file is something you compile with javac? That sounds bonkers, but if you are, just.. add that L. Or, add " before and after the number and pass that to new BigInteger instead, now the number can be thousands of digits large if you want it to be.
Otherwise, you're getting a bytes which either represent the number directly (and the L aspect is not relevant to this conversation), or you're getting a string in, which again, isn't relevant to this conversation: That L is just for writing literal numbers inside .java files, it doesn't come up anywhere else. Turning a string containing digits, such as "20118998631" into e.g. a long is done with Long.parseLong("20118998631") which works fine, and does not require the L (in fact, it won't work if you include it).
As people have already mentioned in the comments, we need more details about your networking in order to answer the question in full.
In general:
Your respons will be in form of a string (or byte array to be exact) and you will have to convert this to your representation.
You will have to use a function to convert the string to your desired representation, for example, Long.valueOf("20118998631") would do it.
But depending on the setup in use you might need to configure your networking to interpret the incoming number as long.
In general, most developers tend to use int for most things, so you might have code in your networking that tries to convert all numbers to int, which will not work with numbers larger than 2147483647, no matter what. The StackTrace should help in this case.
For the examples provided in your question:
int x = 20118998631;
/*
compilation error, the number doesn't fit within an integer and never will.
Therefore expected.
*/
long l = 20118998631;
/*
compilation error, you assign to the variable l the integer constant 20118998631;
this will not work as the given integer is larger than max int.
Use 20118998631L (not the L) to use a long
*/
double d = 20118998631;
/*
compilation error, same as with long above, use a capital D to interpret the number as double
*/
Long l1 = new Long(20118998631);
/*
compilation error
Same as with long above, you declare an integer constant larger than max int and box it within long.
Add a trailing L for long and preferably remove the boxing (java will auto-box if necessary)
*/
So 20118998631L = 0x4_AF2F_8E67L which does not fit in a java int of 4 bytes, only in a long.
The REST API defines an INT and indeed in an SQL INT this might fit.
Getting the "INT" as String s you must do Long.parseLong(s).
Getting the "INT" as bytes, then 04 might be a size (4 bytes), of 2939129447.
I am working with data types at the moment in Java, and if I have understood correctly the type long accepts a value between the ranges of -9,223,372,036,854,775,808 to +9,223,372,036,854,775,807. Now as you can see below, I have create a long variable called testLong, although when I insert 9223372036854775807 as the value, I get an error stating:
The literal 9223372036854775807 of the type int is out of range.
I don't know why it is referring to the long data type as an int.
Anyone have any ideas?
Code:
char testChar = 01;
byte testByte = -128;
int testInt = -2147483648;
short testShort = -32768;
long testLong = 9223372036854775807;
float testFoat;
double testDouble = 4.940656458412;
boolean testBool = true;
Add a capital L to the end:
long value = 9223372036854775807L;
Otherwise, the compiler will try to parse the literal as an int, hence the error message
I don't know why it is referring to the long data type as an int
It is not. You should learn to trust compiler messages (especially when they are from sane, modern compilers and not ancient compilers that tended to have bad error messages). While the language that they speak might be hard to decipher at times, they are not usually lying to you.
Let's look at it again:
The literal of int 9223372036854775807 is out of range.
Note, that it doesn't mention your variable testLong or the type long anywhere, so the problem is not about the initialization. It seems to occur at some other point.
Now lets investigate some of the parts of the message:
int tells us that he wants to treat something as an int value (which is not what you wanted!)
"out of range" is pretty clear: something is not within the expected range (probably that of int)
"The literal": now that's interesting: what is a literal?
I'll leave the cozy list to talk about literals for a moment: literals are places where you have some value in your code. There are String literals, int literals, class literals and so on. Every time you mention a value explicitly in your code, it's a literal.
So it's not actually nagging you about the variable declaration, but the number itself, the value is what it's nagging you about.
You can easily verify this by using the same literal in a context where a long and an int are equally acceptable:
System.out.println(9223372036854775807);
PrintStream.println can take either an int or a long (or pretty much anything else). So that code should be fine, right?
No. Well, maybe it should be, but according to the rules it is not fine.
The problem is that "some digits" is defined to be an int literal and therefore must be in the range defined by int.
If you want to write a long literal, then you must make that explicit by appending the L (or lower case l, but I highly suggest you always use the upper-case variant, because it's much easier to read and harder to mistake for a 1).
Note that a similar problem occurs with float (postfix F/f) and double (postfix D/d).
Side note: you'll realize that there are no byte or short literals and you can still assign values (usually int literals) to byte and short variables: that's possible due to special rules in § 5.2 about conversions in an Assignment Contexts: they allow assignment of constant expressions of a larger type to byte, short, char or int if the values are within the types range.
Try doing 9223372036854775807L. The L at the end tells Java that 9223372036854775807 is a long.
I had this problem in the past and I fixed that by writing the value in the scientific form.
for example:
double val = 9e300;
long ak = 34778754226788444L/l;
Both use but at a time only one use uppercase L or lowercase l.
Why use L/l? Because long is a part of integral datatype.
I am working with data types at the moment in Java, and if I have understood correctly the type long accepts a value between the ranges of -9,223,372,036,854,775,808 to +9,223,372,036,854,775,807. Now as you can see below, I have create a long variable called testLong, although when I insert 9223372036854775807 as the value, I get an error stating:
The literal 9223372036854775807 of the type int is out of range.
I don't know why it is referring to the long data type as an int.
Anyone have any ideas?
Code:
char testChar = 01;
byte testByte = -128;
int testInt = -2147483648;
short testShort = -32768;
long testLong = 9223372036854775807;
float testFoat;
double testDouble = 4.940656458412;
boolean testBool = true;
Add a capital L to the end:
long value = 9223372036854775807L;
Otherwise, the compiler will try to parse the literal as an int, hence the error message
I don't know why it is referring to the long data type as an int
It is not. You should learn to trust compiler messages (especially when they are from sane, modern compilers and not ancient compilers that tended to have bad error messages). While the language that they speak might be hard to decipher at times, they are not usually lying to you.
Let's look at it again:
The literal of int 9223372036854775807 is out of range.
Note, that it doesn't mention your variable testLong or the type long anywhere, so the problem is not about the initialization. It seems to occur at some other point.
Now lets investigate some of the parts of the message:
int tells us that he wants to treat something as an int value (which is not what you wanted!)
"out of range" is pretty clear: something is not within the expected range (probably that of int)
"The literal": now that's interesting: what is a literal?
I'll leave the cozy list to talk about literals for a moment: literals are places where you have some value in your code. There are String literals, int literals, class literals and so on. Every time you mention a value explicitly in your code, it's a literal.
So it's not actually nagging you about the variable declaration, but the number itself, the value is what it's nagging you about.
You can easily verify this by using the same literal in a context where a long and an int are equally acceptable:
System.out.println(9223372036854775807);
PrintStream.println can take either an int or a long (or pretty much anything else). So that code should be fine, right?
No. Well, maybe it should be, but according to the rules it is not fine.
The problem is that "some digits" is defined to be an int literal and therefore must be in the range defined by int.
If you want to write a long literal, then you must make that explicit by appending the L (or lower case l, but I highly suggest you always use the upper-case variant, because it's much easier to read and harder to mistake for a 1).
Note that a similar problem occurs with float (postfix F/f) and double (postfix D/d).
Side note: you'll realize that there are no byte or short literals and you can still assign values (usually int literals) to byte and short variables: that's possible due to special rules in § 5.2 about conversions in an Assignment Contexts: they allow assignment of constant expressions of a larger type to byte, short, char or int if the values are within the types range.
Try doing 9223372036854775807L. The L at the end tells Java that 9223372036854775807 is a long.
I had this problem in the past and I fixed that by writing the value in the scientific form.
for example:
double val = 9e300;
long ak = 34778754226788444L/l;
Both use but at a time only one use uppercase L or lowercase l.
Why use L/l? Because long is a part of integral datatype.
I have an ArrayList that i am inputting numbers into like
23466012.83
23466413.39
23466411.94
etc.
but when i reprint them from the array after i sort them they are reprinted like this
2.346601283E7
2.346641339E7
2.346641194E7
Why does java do this and how can this be fixed? (I want the format to be the same as when it was input)
Thanks!
Please review how Java handles primitive types and their related objects. By adding a "double" (lowercase) primitive type into a List, they are converted into "Double" objects, because List in Java can only hold objects, not primitives.
Therefore when you later output the Double object, it actually uses the simple toString() method of class Double to format the line. And this is implemented in a way to print the full range of Double in a readable format, this is why it chooses the so-called Scientific Notation with exponents display.
By using a more useful formatter, e.g. the Formatter class as mentioned in the comment or the MessageFormat class, you can better control how the output looks like.
Why does java do this
Java merely prints out your Double values using the default number format.
and how can this be fixed?
By explicitly specifying the desired number format.
I want the format to be the same as when it was input
First of all, you'll need to understand that you can't get "the same format as when it was input" because that information is irretrievably lost. It cannot be determined by inspecting a Double value how many significant digits were used to parse it.
If all you need is printing with two decimal places, one way to achieve it is with this statement:
System.out.format("%.2f%n", 23466012.83);
If, by any chance, you are not bound to using Double as the container of your numeric values, you may also consider BigDecimal, which can exactly represent an arbitrary value in decimal notation. It takes a lot more memory and is a lot slower in computation, but for many use cases neither of those may matter much. A larger issue is that the division of BigDecimal is an involved process because, by default, the API will insist on producing an exact result, which will fail for things as simple as 1/3.
System.out.format("%f%n", value);
Where value is the double primitive variable you want to print to sysout the screen.
Remove the %n if you want to continue printing on the same line.
There are existing answers that indicate how to format the output if you want the numbers output with two decimal places, regardless of how they were input.
If you really mean "I want the format to be the same as when it was input" there is only one practical option - store the input string. You can parse it as a double or BigDecimal for validation and when you need it as input to arithmetic, but always output it using the original.
so when casting like in the statement below :-
int randomNumber=(int) (Math.random()*5)
it causes the random no. generated to get converted into an int..
Also there's this method I just came across Integer.parseInt() which does the same !
i.e return an integer
Why two different ways to make a value an int ?
Also I made a search and it says parseInt() takes string as an argument.. So does this mean that parseInt() is ONLY to convert String into integer ?
What about this casting then (int) ?? Can we use this to convert a string to an int too ?
sorry if it sounds like a dumb question..I am just confused and trying to understand
Help ?
Integer.parseInt does not do the same thing as a cast.
Let's take a look at your first example:
int randomNumber=(int) (Math.random()*5)
Math.random returns a double, and when you multiply a double by an int Java considers the result to be a double. Thus the expression Math.random()*5 has a type of double. What you're trying to do is assign that value to a variable of type int. By default Java will not allow you to assign a double value to a variable of type int without your explicitly telling the compiler that it's ok to do so. Basically you can think of casting a double to an int as telling the compiler, "I know this int variable can't hold the decimal part of this double value, but that's ok, just truncate it."
Now take a look at the conversion of a String to an int:
int value = Integer.parseInt("5");
The string "5" is not immediately convertible to an integer. Unlike doubles, which by definition can be converted to an integer by dropping the decimal part, Strings can't be easily or consistently converted to an int. "5", "042", and "1,000" all have integer representations, but something like "Hello, World!" does not. Because of this there is no first order language feature for converting a String to an int. Instead, you use a method to parse the String and return the value.
So to answer all your questions:
Why two different ways to make a value an int ?
You have to take into account what the type of the value you are converting is. If you're converting a primitive to an int you can use a cast, if you're converting an Object you'll need to use some sort of conversion method specific to that type.
Also I made a search and it says parseInt() takes string as an argument.. So does this mean that parseInt() is ONLY to convert String into integer ?
Correct. You cannot pass any other type to the parseInt method or you will get a compiler error.
What about this casting then (int) ?? Can we use this to convert a string to an int too ?
No, casting to int will only work for primitive values, and in Java a String is not a primitive.
In your example, you are casting a floating-point number to an int. Integer.parseInt(), however, reads an integer value from a String.
You can only cast between compatible types (I'd link to the JLS but that might be too much for a beginner question).
Casting is basically just taking a value and saying, "Hey, this thing that was a double? Now it's an int. So there."
You can't do that with a string because it isn't anything like an int. You have to instead parse an int out of it, which is actually a lot harder than it sounds. Fortunately, it's already implemented for you so you don't have to worry about how it works.
Casting can only convert from one numeric type to another. Interpreting a string (aka parsing) needs to be done with a method call.
Let's start from the top.
int randomNumber=(int) (Math.random()*5);
Yes, this does indeed give a random integer between 0 and 4, but this is very much not the proper way of doing this. You see, if you forget a parenthesis, i.e. you type
int notSoRandomNumber=(int) Math.random()*5;
you'll always get 0 because casting has higher precedence than multiplication. That is to say the result of Math.random() is first coerced into an integer, which will always be 0 and then it's multiplied by 5, which is still 0.
I'd favour using java.util.Random for generating random integers. q.v. http://java.sun.com/javase/6/docs/api/java/util/Random.html#nextInt(int).
Casting can only be done between "compatible types". For primitive types and their wrappers (i.e. int, Integer, long, Long, &c.) you can always cast between them with the caveat that some conversions lose information. e.g. when casting a long to an int, the long may contain a number larger than Integer.MAX_VALUE]. This kind of casting Java basically got from C++ which it in turn got from C.
As for casting objects, it's actually simpler. Simply ask "is this object, o, an X?" If so then (X) o makes sense and has static type X. If o is not an X and you try to cast anyway, you'll get a ClassCastException signifying that o's dynamic (runtime) type is not compatible with X. This will probably make a lot more sense later when you get the difference between the static and the dynamic (runtime) type of objects.
Following code convert String to int without any methods
public class MyStringToNumber {
public static int convert_String_To_Number(String numStr){
char ch[] = numStr.toCharArray();
int sum = 0;
//get ascii value for zero
int zeroAscii = (int)'0'; // '0'=48 zeroAscii=48
for(int i=0;i<ch.length;i++){
int tmpAscii = (int)ch[i]; // for 0 ch[i]=3,3=51, tempAscii=51
// (0*10)+(51-48)
// 0 +3
// 3
// sum=3
// for 1 ch[i]=2,2=50, tempAscii=50
sum = (sum*10)+(tmpAscii-zeroAscii); // 0 +(51-48)=3 sum=3
// (3*10)=30+(50-48)
// 30 + 2
// sum=32
// for 2 ch[i]=5, 5=53 tempAscii=53
// (32*10)+(53-48)
// 320 + 5
// 325
// sum=325
// for 3 ch[i]=6,6=54, tempAscii=54
// (325*10)+(54-48)
// 3250 +6
// 3256
// sum=3256
}
return sum;
}
public static void main(String a[]){
System.out.println("\"3256\" == "+convert_String_To_Number("3256"));
}
}
Output "3256" --> 3256
Parse() method is available is many formats, Integer class having the method ParseInt() which is a static method, we to call this method by Integer.ParseInt()
Similarly Double class having ParseDouble()and we call it as Double.ParseDouble().
The more Generic way is XXXX.ParseXXXX()
The main use of this Method is to convert any Object into a Primitive.
And here you can raise a question why we need to convert into Primitives?
The answer is, we know that primitives are stored in stack area and objects are stored in Heap area, and you doesn't want to waste the Heap Memory and you can convert an Object into a Primitive.
And the other thing, while accessing any Object there may be Overhead.
It is better to use as a Primitive.