Software Engineering for Smart Data Analytics & Smart Data Analytics for Software Engineering
“This cast will always throw a ClassCastException. FindBugs tracks type information from instanceof checks, and also uses more precise information about the types of values returned from methods and loaded from fields. Thus, it may have more precise information that just the declared type of a variable, and can use this to determine that a cast will always throw an exception at runtime.” – 2013-10-13
A common need in strongly typed languages is to convert a value of a certain type into a different type. If the destination type is not equal to or is not a supertype of the source type, a ClassCastException will be thrown.
In most instances, the Java Compiler is unable to validate whether the cast is valid, since the values being cast usually change in runtime. In some cases, however, it is possible to deduct the type of the value to be cast, extracting information from instance of checks, return types of methods and types of fields (results obtained through Points-to Analysis might also be used), which allows impossible casts to be detected prior to runtime.
1. conversions type categories:
A specific conversion from type S to type T allows an expression of type S to be treated at compile time as if it had type T instead. For convenience of description, the specific conversions that are possible in the Java programming language are grouped into several broad categories:
1.1. Identity conversions
A conversion from a type to that same type is permitted for any type.
1.2. Widening primitive conversions
A widening primitive conversion does not lose information about the overall magnitude of a numeric value.
1.3. Narrowing primitive conversions
A narrowing primitive conversion may lose information about the overall magnitude of a numeric value and may also lose precision and range.
1.4. Widening and Narrowing Primitive Conversion
The following conversion combines both widening and narrowing primitive conversions:
• byte to char
First, the byte is converted to an int via widening primitive conversion and then the resulting int is converted to a char by narrowing primitive conversion .
1.5. Widening Reference Conversion
A widening reference conversion exists from any reference type S to any reference type T, provided S is a subtype) of T.
1.6. Narrowing reference conversions
Six kinds of conversions are called the narrowing reference conversions:
conversion from SC to TC.
1.7. Boxing conversions
Boxing conversion converts expressions of primitive type to corresponding expressions of reference type. Specifically, the following nine conversions are called the boxing conversions:
1.8. Unboxing conversions
Unboxing conversion converts expressions of reference type to corresponding expressions of primitive type. Specifically, the following eight conversions are called the unboxing conversions:
1.9. Unchecked conversions
Let G name a generic type declaration with n type parameters. There is an unchecked conversion from the raw class or interface type G to any parameterized type of the form G<T1,…,Tn>. There is an unchecked conversion from the raw array type G[ ] to any array type type of the formG<T1,…,Tn>[ ].
1.10. Capture conversions 1.11. String conversions 1.12. Forbidden Conversions 1.13. Value set conversions
2. Conversion methods:
There are different methods for conversion such as assignment conversion, method invocation conversion, string conversion, casting coversion and etc.
2.1. Casting Conversion Casting conversion is applied to the operand of a cast operator :the type of the operand expression must be converted to the type explicitly named by the cast operator. Casting contexts allow the use of one of:
Each conversion is signified by a symbol:
Casting conversions to reference types
source :http://docs.oracle.com/javase/specs/jls/se7/html/jls-5.html
Here we've tried to deal with this bug but it's a hug area so our detector is not so complete as we face different prolbems such as for each object,which can have different real type base on the latest assignment to that so it is sometime hard to find the real type or maybe impossible.
<code Java> public class ImpossibleCast {
public static Float find() { Object m = buildDouble(); Float g = (Float) m; //Double to Float return g; } public static Float find(Object test) { double doubleVar = 3.14E5 test= doubleVar; Float var = (Float) test; //double to Float return var; }
} </Code>
<code Java> public class FalseImpossibleCast {
public static float find() { Object m = builddouble(); float g = (float) m; //double to float return g; }
} </Code>
Benchmark project | Precision | Recall | ||||
---|---|---|---|---|---|---|
FB | JT | Delta | FB | JT | Delta | |
Project … | …% | …% | …% | …% | …% | …% |
Project … | …% | …% | …% | …% | …% | …% |
FB = FindBugs, JT = JTransformer, Delta = JTransformer - FindBugs