package com.inspirx.mkt;
public class Test<T> {
public T get(Integer i) {
Integer k = i;
return (T)k;
}
public static void main(String[] args) {
Test<String> t = new Test<String>();
t.get(2);
}
}
请问各位大侠以上程序执行为什么不出错,而我把Integer强转成String就出错. 但是以上写法难道不是和强转一个意思吗?
这块不理解了.对泛型了解的不深.请各位前辈指较.
注:return (T)k; 这句话有黄叹号.不知道为什么有,好像是没用到怎么事的.
9 个解决方案
#1
最后一行改为 String str = t.get(2);试试呢
#2
按楼上写法也没有错.
#3
是编译没有错.运行出错了.但是,我认为,在调用Get方法的时候,走到return的时候,要转换成T(Stirng)这步就应该出错了.可为什么它没出错..类型依然是Integer
#4
如果不报错才有问题的,你传入的是一个Integer的对象,你却要在方法内强制转成String的,你说会不会报错????
注:return (T)k; 这句话有黄叹号.不知道为什么有,好像是没用到怎么事的.
只是给你个警告,告诉你这里强制转换可能会在运行的时候报错
注:return (T)k; 这句话有黄叹号.不知道为什么有,好像是没用到怎么事的.
只是给你个警告,告诉你这里强制转换可能会在运行的时候报错
#5
按我一开始发的贴子那种写法,编译,运行都没有错.
按1L的写法,是编译无错,运行有错.
但我认为,我的第一种写法运行就应该出错了.但它没出.所以不理解了.
#6
泛型会在编译期执行类型安全检查,但在运行时 泛型将都由于擦出原因被认作是Object,所以此处的T在运行时只是Object不管你是Integer还是S挺都可以,但是强制类型转换时String就是String,Integer就是Integer,所有会出现编译期异常无法执行!记住泛型在运行期间会被擦出类型!
#7
所以由于类型擦出才会有那种所谓的黄叹号!因为编译期在运行期间无法知道其类型!也是因此你的第一种写法才可以运行,在运行期间它等同于return (Object)i;所以再加上String i = t。get(2);就会出现错误!只能写成Object i = t。get(2);才可以!
#8
看警告就知道是为强制检查的类型转换,有可能运行时抛异常
#9
JAVA的泛型可以说是一种伪泛型,在编译为字节码时会把泛型的类型擦除了,因此
public T get(Integer i) 它的返回类型在编码后变为了Object的类型了,所以它是把Integer强转为Object。
9: iconst_2
10: invokestatic #4 // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
13: invokevirtual #5 // Method get:(Ljava/lang/Integer;)Ljava/lang/Object;
上面这几行是t.get(2);的字节码,从中可以看出invokevirtual指令执行的get方法的返回类型是Object的,传入参数类型是Integer
public T get(Integer i) 它的返回类型在编码后变为了Object的类型了,所以它是把Integer强转为Object。
9: iconst_2
10: invokestatic #4 // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
13: invokevirtual #5 // Method get:(Ljava/lang/Integer;)Ljava/lang/Object;
上面这几行是t.get(2);的字节码,从中可以看出invokevirtual指令执行的get方法的返回类型是Object的,传入参数类型是Integer
#1
最后一行改为 String str = t.get(2);试试呢
#2
按楼上写法也没有错.
#3
是编译没有错.运行出错了.但是,我认为,在调用Get方法的时候,走到return的时候,要转换成T(Stirng)这步就应该出错了.可为什么它没出错..类型依然是Integer
#4
如果不报错才有问题的,你传入的是一个Integer的对象,你却要在方法内强制转成String的,你说会不会报错????
注:return (T)k; 这句话有黄叹号.不知道为什么有,好像是没用到怎么事的.
只是给你个警告,告诉你这里强制转换可能会在运行的时候报错
注:return (T)k; 这句话有黄叹号.不知道为什么有,好像是没用到怎么事的.
只是给你个警告,告诉你这里强制转换可能会在运行的时候报错
#5
按我一开始发的贴子那种写法,编译,运行都没有错.
按1L的写法,是编译无错,运行有错.
但我认为,我的第一种写法运行就应该出错了.但它没出.所以不理解了.
#6
泛型会在编译期执行类型安全检查,但在运行时 泛型将都由于擦出原因被认作是Object,所以此处的T在运行时只是Object不管你是Integer还是S挺都可以,但是强制类型转换时String就是String,Integer就是Integer,所有会出现编译期异常无法执行!记住泛型在运行期间会被擦出类型!
#7
所以由于类型擦出才会有那种所谓的黄叹号!因为编译期在运行期间无法知道其类型!也是因此你的第一种写法才可以运行,在运行期间它等同于return (Object)i;所以再加上String i = t。get(2);就会出现错误!只能写成Object i = t。get(2);才可以!
#8
看警告就知道是为强制检查的类型转换,有可能运行时抛异常
#9
JAVA的泛型可以说是一种伪泛型,在编译为字节码时会把泛型的类型擦除了,因此
public T get(Integer i) 它的返回类型在编码后变为了Object的类型了,所以它是把Integer强转为Object。
9: iconst_2
10: invokestatic #4 // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
13: invokevirtual #5 // Method get:(Ljava/lang/Integer;)Ljava/lang/Object;
上面这几行是t.get(2);的字节码,从中可以看出invokevirtual指令执行的get方法的返回类型是Object的,传入参数类型是Integer
public T get(Integer i) 它的返回类型在编码后变为了Object的类型了,所以它是把Integer强转为Object。
9: iconst_2
10: invokestatic #4 // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
13: invokevirtual #5 // Method get:(Ljava/lang/Integer;)Ljava/lang/Object;
上面这几行是t.get(2);的字节码,从中可以看出invokevirtual指令执行的get方法的返回类型是Object的,传入参数类型是Integer