annotate src/luan/LuanCloner.java @ 1561:e1a13e707bf3

start immutable
author Franklin Schmidt <fschmidt@gmail.com>
date Thu, 05 Nov 2020 20:24:09 -0700
parents e0cf0d108a77
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
1 package luan;
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
2
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
3 import java.util.Map;
1335
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
4 import java.util.Collection;
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
5 import java.util.IdentityHashMap;
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
6
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
7
781
fbbdd369a13a rename DeepCloner to LuanCloner
Franklin Schmidt <fschmidt@gmail.com>
parents: 775
diff changeset
8 public final class LuanCloner {
785
d69d3c51c44e more work on incremental cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 784
diff changeset
9 public enum Type { COMPLETE, INCREMENTAL }
d69d3c51c44e more work on incremental cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 784
diff changeset
10
d69d3c51c44e more work on incremental cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 784
diff changeset
11 public final Type type;
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
12 private final Map cloned = new IdentityHashMap();
1335
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
13 private Luan luan = null;
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
14
785
d69d3c51c44e more work on incremental cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 784
diff changeset
15 public LuanCloner(Type type) {
d69d3c51c44e more work on incremental cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 784
diff changeset
16 this.type = type;
782
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
17 }
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
18
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
19 public LuanCloneable clone(LuanCloneable obj) {
195
24ede40ee0aa make MetatableGetter DeepCloneable, scoped, and secure
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 171
diff changeset
20 if( obj==null )
24ede40ee0aa make MetatableGetter DeepCloneable, scoped, and secure
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 171
diff changeset
21 return null;
781
fbbdd369a13a rename DeepCloner to LuanCloner
Franklin Schmidt <fschmidt@gmail.com>
parents: 775
diff changeset
22 LuanCloneable rtn = (LuanCloneable)cloned.get(obj);
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
23 if( rtn == null ) {
1335
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
24 if( obj instanceof Luan ) {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
25 if( luan != null )
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
26 throw new RuntimeException("2 luans in "+type+" "+this+" - "+luan+" "+obj);
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
27 luan = (Luan)obj;
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
28 }
784
6a7c6879158d revert shallowClone()
Franklin Schmidt <fschmidt@gmail.com>
parents: 782
diff changeset
29 rtn = obj.shallowClone();
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
30 cloned.put(obj,rtn);
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
31 obj.deepenClone(rtn,this);
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
32 }
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
33 return rtn;
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
34 }
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
35
782
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
36 public Object[] clone(Object[] obj) {
1561
e1a13e707bf3 start immutable
Franklin Schmidt <fschmidt@gmail.com>
parents: 1335
diff changeset
37 if( obj==null || obj.length == 0 )
78
7c08b611125d better deep cloning
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 77
diff changeset
38 return obj;
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
39 Object[] rtn = (Object[])cloned.get(obj);
78
7c08b611125d better deep cloning
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 77
diff changeset
40 if( rtn == null ) {
7c08b611125d better deep cloning
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 77
diff changeset
41 rtn = obj.clone();
7c08b611125d better deep cloning
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 77
diff changeset
42 cloned.put(obj,rtn);
7c08b611125d better deep cloning
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 77
diff changeset
43 for( int i=0; i<rtn.length; i++ ) {
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
44 rtn[i] = get(rtn[i]);
78
7c08b611125d better deep cloning
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 77
diff changeset
45 }
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
46 }
78
7c08b611125d better deep cloning
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents: 77
diff changeset
47 return rtn;
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
48 }
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
49
782
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
50 public Map clone(Map obj) {
1561
e1a13e707bf3 start immutable
Franklin Schmidt <fschmidt@gmail.com>
parents: 1335
diff changeset
51 if( obj==null )
e1a13e707bf3 start immutable
Franklin Schmidt <fschmidt@gmail.com>
parents: 1335
diff changeset
52 return null;
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
53 Map rtn = (Map)cloned.get(obj);
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
54 if( rtn == null ) {
1335
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
55 try {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
56 rtn = obj.getClass().newInstance();
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
57 } catch(InstantiationException e) {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
58 throw new RuntimeException(e);
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
59 } catch(IllegalAccessException e) {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
60 throw new RuntimeException(e);
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
61 }
1561
e1a13e707bf3 start immutable
Franklin Schmidt <fschmidt@gmail.com>
parents: 1335
diff changeset
62 cloned.put(obj,rtn);
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
63 for( Object stupid : obj.entrySet() ) {
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
64 Map.Entry entry = (Map.Entry)stupid;
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
65 rtn.put( get(entry.getKey()), get(entry.getValue()) );
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
66 }
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
67 }
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
68 return rtn;
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
69 }
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
70
1335
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
71 public Collection clone(Collection obj) {
1561
e1a13e707bf3 start immutable
Franklin Schmidt <fschmidt@gmail.com>
parents: 1335
diff changeset
72 if( obj==null )
e1a13e707bf3 start immutable
Franklin Schmidt <fschmidt@gmail.com>
parents: 1335
diff changeset
73 return null;
1335
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
74 Collection rtn = (Collection)cloned.get(obj);
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
75 if( rtn == null ) {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
76 try {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
77 rtn = obj.getClass().newInstance();
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
78 } catch(InstantiationException e) {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
79 throw new RuntimeException(e);
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
80 } catch(IllegalAccessException e) {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
81 throw new RuntimeException(e);
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
82 }
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
83 for( Object entry : (Collection)obj ) {
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
84 rtn.add( get(entry) );
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
85 }
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
86 }
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
87 return rtn;
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
88 }
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
89
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
90 public Object get(Object obj) {
781
fbbdd369a13a rename DeepCloner to LuanCloner
Franklin Schmidt <fschmidt@gmail.com>
parents: 775
diff changeset
91 if( obj instanceof LuanCloneable )
782
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
92 return clone((LuanCloneable)obj);
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
93 if( obj instanceof Object[] )
782
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
94 return clone((Object[])obj);
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
95 if( obj instanceof Map )
782
655280eab1e2 start limited cloning
Franklin Schmidt <fschmidt@gmail.com>
parents: 781
diff changeset
96 return clone((Map)obj);
1335
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
97 if( obj instanceof Collection )
e0cf0d108a77 major cleanup
Franklin Schmidt <fschmidt@gmail.com>
parents: 785
diff changeset
98 return clone((Collection)obj);
433
c6bcb8859b93 make LuanState.registry a Map;
Franklin Schmidt <fschmidt@gmail.com>
parents: 195
diff changeset
99 return obj;
77
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
100 }
4bf3d0c0b6b9 make LuanState cloneable
fschmidt@gmail.com <fschmidt@gmail.com@21e917c8-12df-6dd8-5cb6-c86387c605b9>
parents:
diff changeset
101 }