论坛首页 Java企业应用论坛

诡异代码,麻烦各位大牛看下【泛型】

浏览 11178 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
   发表时间:2011-12-01  
严重同意2楼的说法。
对于List lst = new ArrayList<String>()这种代码,你要么写成
List<String> lst = new ArrayList<String>();
要么写成
List lst = new ArrayList();

写成这种List lst = new ArrayList<String>()的人真不知道说什么好。
另外都new ArrayList<String>()了还add(1);


你如果是为了研究JDK的泛型那值得鼓励,说明你热爱学习。
你如果是在日常开发中遇到这样的问题,只能说你对Java还没入门,要我是老板,你把代码写成这样我直接开除你。
0 请登录后投票
   发表时间:2011-12-01  
严重同意2楼的说法。
对于List lst = new ArrayList<String>()这种代码,你要么写成
List<String> lst = new ArrayList<String>();
要么写成List lst = new ArrayList();
写成这种List lst = new ArrayList<String>()的人真不知道说什么好。
另外都new ArrayList<String>()了还add(1);

你如果是为了研究JDK的泛型那值得鼓励,说明你热爱学习。
你如果是在日常开发中遇到这样的问题,只能说你对Java还没入门,要我是老板,你把代码写成这样我直接开除你。
0 请登录后投票
   发表时间:2011-12-01  
mfkvfn 写道
严重同意2楼的说法。
对于List lst = new ArrayList<String>()这种代码,你要么写成
List<String> lst = new ArrayList<String>();
要么写成List lst = new ArrayList();
写成这种List lst = new ArrayList<String>()的人真不知道说什么好。
另外都new ArrayList<String>()了还add(1);

你如果是为了研究JDK的泛型那值得鼓励,说明你热爱学习。
你如果是在日常开发中遇到这样的问题,只能说你对Java还没入门,要我是老板,你把代码写成这样我直接开除你。



靠,你也太狠了。你要是老板我就不在你下面干!教育下不可以吗
0 请登录后投票
   发表时间:2011-12-01  
编译后调用的处理的方式不一样,
一个是调用java.io.PrintStream.println(java.lang.String)并且进行了checkcast java.lang.String [44]
一个是调用java.io.PrintStream.println(java.lang.Object)

 
// Method descriptor #6 ()V
  // Stack: 3, Locals: 3
  private static void test();
     0  new java.util.ArrayList [15]
     3  dup
     4  invokespecial java.util.ArrayList() [17]
     7  astore_0 [lst]
     8  aload_0 [lst]
     9  ldc <String "Test005"> [18]
    11  invokeinterface java.util.List.add(java.lang.Object) : boolean [20] [nargs: 2]
    16  pop
    17  aload_0 [lst]
    18  iconst_3
    19  invokestatic java.lang.Integer.valueOf(int) : java.lang.Integer [26]
    22  invokeinterface java.util.List.add(java.lang.Object) : boolean [20] [nargs: 2]
    27  pop
    28  aload_0 [lst]
    29  astore_1 [ls]
    30  aload_1 [ls]
    31  ldc <String "Test0051"> [32]
    33  invokeinterface java.util.List.add(java.lang.Object) : boolean [20] [nargs: 2]
    38  pop
    39  iconst_0
    40  istore_2 [i]
    41  goto 63
    44  getstatic java.lang.System.out : java.io.PrintStream [34]
    47  aload_1 [ls]
    48  iload_2 [i]
    49  invokeinterface java.util.List.get(int) : java.lang.Object [40] [nargs: 2]
    54  checkcast java.lang.String [44]
    57  invokevirtual java.io.PrintStream.println(java.lang.String) : void [46]

    60  iinc 2 1 [i]
    63  iload_2 [i]
    64  aload_1 [ls]
    65  invokeinterface java.util.List.size() : int [52] [nargs: 1]
    70  if_icmplt 44
    73  return
      Line numbers:
        [pc: 0, line: 9]
        [pc: 8, line: 11]
        [pc: 17, line: 12]
        [pc: 28, line: 13]
        [pc: 30, line: 14]
        [pc: 39, line: 15]
        [pc: 44, line: 16]
        [pc: 60, line: 15]
        [pc: 73, line: 18]
      Local variable table:
        [pc: 8, pc: 74] local: lst index: 0 type: java.util.List
        [pc: 30, pc: 74] local: ls index: 1 type: java.util.List
        [pc: 41, pc: 73] local: i index: 2 type: int
      Local variable type table:
        [pc: 30, pc: 74] local: ls index: 1 type: java.util.List<java.lang.String>
 
  // Method descriptor #6 ()V
  // Stack: 3, Locals: 3
  public static void test1();
     0  new java.util.ArrayList [15]
     3  dup
     4  invokespecial java.util.ArrayList() [17]
     7  astore_0 [lst]
     8  aload_0 [lst]
     9  ldc <String "Test005"> [18]
    11  invokeinterface java.util.List.add(java.lang.Object) : boolean [20] [nargs: 2]
    16  pop
    17  aload_0 [lst]
    18  iconst_3
    19  invokestatic java.lang.Integer.valueOf(int) : java.lang.Integer [26]
    22  invokeinterface java.util.List.add(java.lang.Object) : boolean [20] [nargs: 2]
    27  pop
    28  aload_0 [lst]
    29  astore_1 [ls]
    30  aload_1 [ls]
    31  iconst_1
    32  invokestatic java.lang.Integer.valueOf(int) : java.lang.Integer [26]
    35  invokeinterface java.util.List.add(java.lang.Object) : boolean [20] [nargs: 2]
    40  pop
    41  iconst_0
    42  istore_2 [i]
    43  goto 62
    46  getstatic java.lang.System.out : java.io.PrintStream [34]
    49  aload_1 [ls]
    50  iload_2 [i]
    51  invokeinterface java.util.List.get(int) : java.lang.Object [40] [nargs: 2]
   56  invokevirtual java.io.PrintStream.println(java.lang.Object) : void [64]
    59  iinc 2 1 [i]
    62  iload_2 [i]
    63  aload_1 [ls]
    64  invokeinterface java.util.List.size() : int [52] [nargs: 1]
    69  if_icmplt 46
    72  return
      Line numbers:
        [pc: 0, line: 21]
        [pc: 8, line: 23]
        [pc: 17, line: 24]
        [pc: 28, line: 25]
        [pc: 30, line: 26]
        [pc: 41, line: 27]
        [pc: 46, line: 28]
        [pc: 59, line: 27]
        [pc: 72, line: 30]
      Local variable table:
        [pc: 8, pc: 73] local: lst index: 0 type: java.util.List
        [pc: 30, pc: 73] local: ls index: 1 type: java.util.List
        [pc: 43, pc: 72] local: i index: 2 type: int
      Local variable type table:
        [pc: 30, pc: 73] local: ls index: 1 type: java.util.List<java.lang.Integer>
0 请登录后投票
   发表时间:2011-12-01   最后修改:2011-12-01
对着呢 我只看了第一个 你System.out.println(ls.get(i)); 其中ls.get()方法 返回的是Object哈所以无错
你换成 for(Integer in :ls){
System.out.println(in);
      }
他会报转型的错哈。。。。
再说你定义第一个List时lst 并没有确定压入的类型哈 
0 请登录后投票
   发表时间:2011-12-01  
zhaohongwei1982 写道
PrintStream类中有println(Object x), println(String x),但是没有println(Integer x)

List<Integer> ls = lst;
执行的是println(Object x),先执行String.valueOf(x), 然后再用print(String)打印,所以不会出错。

List<String> ls = lst; 
执行的是println(String x)方法,Integer转String出错。

这楼说的靠谱
0 请登录后投票
   发表时间:2011-12-01  
class文件反编译下就知道了!
0 请登录后投票
   发表时间:2011-12-01  
葬雪晴 写道
泛型擦除+转换异常而已。。

java的泛型是伪泛型。只是编译的时候用以检查而已。。
当需要输出的时候。会强转为需要的类型。
如果类型不匹配转换不了。则会报转换异常

感觉说的额不是特别严谨, 在输出的时候,并不会强制转换为需要的类型吧, 只是在优化的时候,认为是需要的类型,上面第一个的之所以出错是因为ls 在申明的时候指定了List<String> , 所以在使用的时候,他都认为他里面的是String,而不会调用println(Object obj);所以也导致异常了,正如上面所说的,看了源码一切都清楚了
0 请登录后投票
   发表时间:2011-12-01  
huanglei7211 写道
请各位先猜下结果,然后执行代码
代码一:
import java.util.ArrayList;
import java.util.List;

public class Test004 {
	public static void main(String[] args) {
		List lst = new ArrayList<String>();
		lst.add(1);
		lst.add("Test004");
		List<Integer> ls = lst;
		ls.add(2);
		for (int i = 0; i < ls.size(); i++) {
			System.out.println(ls.get(i));
		}
	}
}

代码二:
import java.util.ArrayList;
import java.util.List;

public class Test005 {
	public static void main(String[] args) {
		List lst = new ArrayList<String>();
		lst.add(1);
		lst.add("Test004");
		List<String> ls = lst;
		ls.add("Test0041");
		for (int i = 0; i < ls.size(); i++) {
			System.out.println(ls.get(i));
		}
	}
}


执行命令
javap -c Test

代码一有如下指令:
   56:  invokevirtual   #43; //Method java/io/PrintStream.println:(Ljava/lang/Ob
ject;)V
代码二有如下指令:
   57:  invokevirtual   #47; //Method java/io/PrintStream.println:(Ljava/lang/St
ring;)V

代码二会出现类型转换(Integer转String)错误
0 请登录后投票
   发表时间:2011-12-02   最后修改:2011-12-02
budairenqin 写道
huanglei7211 写道
请各位先猜下结果,然后执行代码
代码一:
import java.util.ArrayList;
import java.util.List;

public class Test004 {
	public static void main(String[] args) {
		List lst = new ArrayList<String>();
		lst.add(1);
		lst.add("Test004");
		List<Integer> ls = lst;
		ls.add(2);
		for (int i = 0; i < ls.size(); i++) {
			System.out.println(ls.get(i));
		}
	}
}

代码二:
import java.util.ArrayList;
import java.util.List;

public class Test005 {
	public static void main(String[] args) {
		List lst = new ArrayList<String>();
		lst.add(1);
		lst.add("Test004");
		List<String> ls = lst;
		ls.add("Test0041");
		for (int i = 0; i < ls.size(); i++) {
			System.out.println(ls.get(i));
		}
	}
}


执行命令
javap -c Test

代码一有如下指令:
   56:  invokevirtual   #43; //Method java/io/PrintStream.println:(Ljava/lang/Ob
ject;)V
代码二有如下指令:
   57:  invokevirtual   #47; //Method java/io/PrintStream.println:(Ljava/lang/St
ring;)V

代码二会出现类型转换(Integer转String)错误


有点疑问,调用重载方法,编译期间就确定了么 ?
是不是 integer 和 string 都是 final 的,容易确定,所以就在编译期间确定了
0 请登录后投票
论坛首页 Java企业应用版

跳转论坛:
Global site tag (gtag.js) - Google Analytics