Static代码块引用问题

原创
2016/05/06 14:42
阅读数 190

static代码块里的内容是在类初次调用时就初始化的一堆代码,如果代码块里初始化的是对象,当后期改变对象的属性时,代码块里初始的这些对象的值会跟着改变吗?!我预想的是跟着改变的,因为是同一个对象,即同一个引用。但素……我就写一个简单的测试小程序,结果就不如我愿。

1.实体类Person.java:

package StaticTest;

public class Person {
	private String name;
	private int age;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public Person() {
	}

	public Person(String name, int age) {
		super();
		this.name = name;
		this.age = age;
	}

	@Override
	public String toString() {
		return name + "--" + age;
	}

}

2.测试类Test3.java:

package StaticTest;

import java.util.Collection;
import java.util.HashMap;
import java.util.Map;

public class Test3 {
	private static Map<String, Person> map = new HashMap<String, Person>();

	static {
		map.put("a", new Person("hui", 1));
		map.put("b", new Person("bao", 2));
		System.out.println("Test3" + map);
	}

	public static Collection<Person> getMap() {
		return map.values();
	}

	public static Map<String, Person> change() {
		Map<String, Person> map1 = new HashMap<String, Person>();
		map1.put("a", new Person("huihui", 3));
		map1.put("b", new Person("baobao", 4));

		map.putAll(map1);
		return map;
	}

	public static Map<String, Person> change2() {
		Person a = map.get("a");
		a.setName("huihuihui");
		Person b = map.get("b");
		b.setName("baobaobao");
		return map;
	}

	public static void main(String[] args) {
		System.out.println(change());
		System.out.println(map);
		System.out.println(change2());
		System.out.println(map);
	}
}

3.测试类Test33.java:

package StaticTest;

import java.util.HashMap;
import java.util.Map;

public class Test33 {
	private static Map<String, Person> map = new HashMap<String, Person>();

	static {
		for (Person o : Test3.getMap()) {
			map.put(o.getName(), o);
		}
		System.out.println("Test33" + map);
	}

	public static void main(String[] args) {
		System.out.println(Test3.change());
		System.out.println(map.values());

		System.out.println(Test3.change2());
		System.out.println(map.values());

	}
}

测试结果如下:

Test3{a=hui--1, b=bao--2}

Test33{bao=bao--2, hui=hui--1}

{a=huihui--3, b=baobao--4}

[bao--2, hui--1]

{a=huihuihui--3, b=baobaobao--4}

[bao--2, hui--1]

即无论调用change()还是change2(),map.values始终是改变前的值。change()不改变正常,因为添加的Person对象是重新new的,但change2()不应该啊。多番思考、询问,最后发现问题出在:首先调用了change(),这导致map里指向的对象已经发生改变。

图如下:

map-->a-->p1

map-->b-->p2

然而当调用了change()后,a不再指向p1,b也不再指向p2了,所以,这时候,即便你再调用change2()方法,将拿到的对象重新set属性,set的也是后来指向的对象了,不再是修改的p1和p2的属性,故map.values始终不变。

这时将System.out.println(Test3.change());注释掉,想要的效果就会出来了。

展开阅读全文
加载中
点击加入讨论🔥(1) 发布并加入讨论🔥
打赏
1 评论
1 收藏
2
分享
返回顶部
顶部