1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 package org.millscript.millscript.datatypes;
23
24 import org.millscript.commons.util.IList;
25 import org.millscript.commons.util.IMap;
26 import org.millscript.commons.util.ListIterator;
27 import org.millscript.commons.util.Maplet;
28 import org.millscript.commons.util.list.IEmptyList;
29 import org.millscript.commons.util.list.IJavaUtilList;
30 import org.millscript.commons.util.list.IMapletList;
31 import org.millscript.commons.util.list.IStringList;
32 import org.millscript.commons.util.maplet.IMapEntryMaplet;
33 import org.millscript.commons.vfs.VEntry;
34 import org.millscript.commons.vfs.VFolder;
35 import org.millscript.millscript.alert.Alerts;
36
37 import java.util.ArrayList;
38 import java.util.List;
39 import java.util.Map;
40
41 /**
42 * This is a utility class for constructing lists from objects.
43 */
44 public abstract class ListFactory {
45
46 /**
47 * Returns a list made from the specified object.
48 *
49 * @param obj the object to make a list from
50 * @return a List made from the specified object
51 */
52 @SuppressWarnings( "unchecked" )
53 public static final IList make( final Object obj ) {
54 if ( obj instanceof IList ) {
55
56 return (IList) obj;
57 } else if ( obj instanceof List ) {
58
59 return new IJavaUtilList< Object >( (List) obj );
60 } else if ( obj instanceof String ) {
61
62 return new IStringList( (String) obj );
63 } else if ( obj instanceof Maplet ) {
64
65 return new IMapletList< Object >( (Maplet) obj );
66 } else if ( obj instanceof Map.Entry ) {
67
68 return new IMapletList< Object >(
69 new IMapEntryMaplet< Object, Object >( (Map.Entry) obj )
70 );
71 } else if ( obj instanceof IMap ) {
72 return ((IMap) obj).valueList( true );
73 } else if ( obj instanceof ListAware ) {
74 return ((ListAware)obj).asList();
75 } else if ( obj instanceof VFolder ) {
76
77
78 final java.util.List< VEntry > entries = ((VFolder) obj).listEntries();
79 if ( entries == null ) {
80 return IEmptyList.EMPTY_LIST;
81 } else {
82 return new IJavaUtilList< VEntry >( entries );
83 }
84 } else {
85 throw(
86 Alerts.eval(
87 "Cannot create list view for this object",
88 "Not all classes can be viewed as lists"
89 ).culprit( "object", obj ).mishap()
90 );
91 }
92 }
93
94 /**
95 * Checks if the two specified arguments are of the same type, but only for
96 * list compatible types.
97 *
98 * @param x first object to compare
99 * @param y second object to compare
100 * @return <code>true</code> if both objects are of the same type and list
101 * compatible, <code>false</code> otherwise
102 */
103 public static final boolean sameAs( final Object x, final Object y ) {
104 return (
105 x instanceof IList && y instanceof IList ||
106 x instanceof List && y instanceof List ||
107 x instanceof String && y instanceof String ||
108 x instanceof Maplet && y instanceof Maplet ||
109 x instanceof Map.Entry && y instanceof Map.Entry ||
110 x instanceof ListAware && ((ListAware)x).sameAs( y )
111 );
112 }
113
114 /**
115 * Returns an object of the specified type, made from the specified list.
116 * This operation is essentially the reverse of the <code>make</code>
117 * method, above. e.g. if the target type is a String, the list is taken to
118 * be a list of characters making up a new string.
119 *
120 * @param obj the target object type
121 * @param x the list of constituent parts
122 * @return an object of the target type, made from the specified list
123 */
124 public static final Object unmake( final Object obj, final IList< ? > x ) {
125 if ( obj instanceof String ) {
126 StringBuffer buff = new StringBuffer( x.size() );
127 ListIterator< ? > it = x.iterator( true );
128 while ( it.hasNext() ) {
129 buff.append( ( (Character)it.nextValue() ).charValue() );
130 }
131 return buff.toString();
132 } else if ( obj instanceof IList ) {
133 return x;
134 } else if ( obj instanceof List ) {
135 final ArrayList< Object > list = new ArrayList< Object >( x.size() );
136 ListIterator< ? > it = x.iterator( true );
137 while ( it.hasNext() ) {
138 list.add( it.nextValue() );
139 }
140 return list;
141 } else if ( obj instanceof ListAware ) {
142 return ((ListAware)obj).asOriginal( x );
143 } else {
144 throw(
145 Alerts.eval(
146 "Cannot undo list conversion",
147 "Not all classes have reversible list conversions"
148 ).culprit( "object", obj ).mishap()
149 );
150 }
151 }
152
153 /**
154 * Hidden constructor.
155 */
156 private ListFactory() {
157 }
158
159 }