001: /*
002: * $Id: UtilMisc.java,v 1.6 2003/10/15 06:18:17 ajzeneski Exp $
003: *
004: * Copyright (c) 2001, 2002 The Open For Business Project - www.ofbiz.org
005: *
006: * Permission is hereby granted, free of charge, to any person obtaining a
007: * copy of this software and associated documentation files (the "Software"),
008: * to deal in the Software without restriction, including without limitation
009: * the rights to use, copy, modify, merge, publish, distribute, sublicense,
010: * and/or sell copies of the Software, and to permit persons to whom the
011: * Software is furnished to do so, subject to the following conditions:
012: *
013: * The above copyright notice and this permission notice shall be included
014: * in all copies or substantial portions of the Software.
015: *
016: * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
017: * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
018: * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
019: * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
020: * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT
021: * OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR
022: * THE USE OR OTHER DEALINGS IN THE SOFTWARE.
023: */
024: package org.ofbiz.base.util;
025:
026: import java.util.ArrayList;
027: import java.util.Collection;
028: import java.util.Collections;
029: import java.util.HashMap;
030: import java.util.Iterator;
031: import java.util.LinkedList;
032: import java.util.List;
033: import java.util.Locale;
034: import java.util.Map;
035: import java.util.TreeMap;
036:
037: /**
038: * UtilMisc - Misc Utility Functions
039: *
040: * @author <a href="mailto:jonesde@ofbiz.org">David E. Jones</a>
041: * @author <a href="mailto:jaz@ofbiz.org">Andy Zeneski</a>
042: * @version $Revision: 1.6 $
043: * @since 2.0
044: */
045: public class UtilMisc {
046:
047: public static final String module = UtilMisc.class.getName();
048:
049: /**
050: * Get an iterator from a collection, returning null if collection is null
051: * @param col The collection to be turned in to an iterator
052: * @return The resulting Iterator
053: */
054: public static Iterator toIterator(Collection col) {
055: if (col == null)
056: return null;
057: else
058: return col.iterator();
059: }
060:
061: /**
062: * Create a map from passed nameX, valueX parameters
063: * @return The resulting Map
064: */
065: public static Map toMap(String name1, Object value1) {
066: return new UtilMisc.SimpleMap(name1, value1);
067:
068: /* Map fields = new HashMap();
069: fields.put(name1, value1);
070: return fields;*/
071: }
072:
073: /**
074: * Create a map from passed nameX, valueX parameters
075: * @return The resulting Map
076: */
077: public static Map toMap(String name1, Object value1, String name2,
078: Object value2) {
079: return new UtilMisc.SimpleMap(name1, value1, name2, value2);
080:
081: /* Map fields = new HashMap();
082: fields.put(name1, value1);
083: fields.put(name2, value2);
084: return fields;*/
085: }
086:
087: /**
088: * Create a map from passed nameX, valueX parameters
089: * @return The resulting Map
090: */
091: public static Map toMap(String name1, Object value1, String name2,
092: Object value2, String name3, Object value3) {
093: return new UtilMisc.SimpleMap(name1, value1, name2, value2,
094: name3, value3);
095:
096: /* Map fields = new HashMap();
097: fields.put(name1, value1);
098: fields.put(name2, value2);
099: fields.put(name3, value3);
100: return fields;*/
101: }
102:
103: /**
104: * Create a map from passed nameX, valueX parameters
105: * @return The resulting Map
106: */
107: public static Map toMap(String name1, Object value1, String name2,
108: Object value2, String name3, Object value3, String name4,
109: Object value4) {
110: return new UtilMisc.SimpleMap(name1, value1, name2, value2,
111: name3, value3, name4, value4);
112:
113: /* Map fields = new HashMap();
114: fields.put(name1, value1);
115: fields.put(name2, value2);
116: fields.put(name3, value3);
117: fields.put(name4, value4);
118: return fields;*/
119: }
120:
121: /**
122: * Create a map from passed nameX, valueX parameters
123: * @return The resulting Map
124: */
125: public static Map toMap(String name1, Object value1, String name2,
126: Object value2, String name3, Object value3, String name4,
127: Object value4, String name5, Object value5) {
128: Map fields = new HashMap();
129:
130: fields.put(name1, value1);
131: fields.put(name2, value2);
132: fields.put(name3, value3);
133: fields.put(name4, value4);
134: fields.put(name5, value5);
135: return fields;
136: }
137:
138: /**
139: * Create a map from passed nameX, valueX parameters
140: * @return The resulting Map
141: */
142: public static Map toMap(String name1, Object value1, String name2,
143: Object value2, String name3, Object value3, String name4,
144: Object value4, String name5, Object value5, String name6,
145: Object value6) {
146: Map fields = new HashMap();
147:
148: fields.put(name1, value1);
149: fields.put(name2, value2);
150: fields.put(name3, value3);
151: fields.put(name4, value4);
152: fields.put(name5, value5);
153: fields.put(name6, value6);
154: return fields;
155: }
156:
157: /**
158: * Create a map from passed nameX, valueX parameters
159: * @return The resulting Map
160: */
161: public static Map toMap(Object[] data) {
162: if (data == null) {
163: return null;
164: }
165: if (data.length % 2 == 1) {
166: throw new IllegalArgumentException(
167: "You must pass an even sized array to the toMap method");
168: }
169: Map map = new HashMap();
170: for (int i = 0; i < data.length;) {
171: map.put(data[i++], data[i++]);
172: }
173: return map;
174: }
175:
176: /**
177: * Sort a List of Maps by specified consistent keys.
178: * @param listOfMaps List of Map objects to sort.
179: * @param sortKeys List of Map keys to sort by.
180: * @return a new List of sorted Maps.
181: */
182: public static List sortMaps(List listOfMaps, List sortKeys) {
183: if (listOfMaps == null || sortKeys == null)
184: return null;
185: List toSort = new LinkedList(listOfMaps);
186: try {
187: MapComparator mc = new MapComparator(sortKeys);
188: Collections.sort(toSort, mc);
189: } catch (Exception e) {
190: Debug.logError(e,
191: "Problems sorting list of maps; returning null.",
192: module);
193: return null;
194: }
195: return toSort;
196: }
197:
198: /**
199: * Create a list from passed objX parameters
200: * @return The resulting List
201: */
202: public static List toList(Object obj1) {
203: List list = new ArrayList(1);
204:
205: list.add(obj1);
206: return list;
207: }
208:
209: /**
210: * Create a list from passed objX parameters
211: * @return The resulting List
212: */
213: public static List toList(Object obj1, Object obj2) {
214: List list = new ArrayList(2);
215:
216: list.add(obj1);
217: list.add(obj2);
218: return list;
219: }
220:
221: /**
222: * Create a list from passed objX parameters
223: * @return The resulting List
224: */
225: public static List toList(Object obj1, Object obj2, Object obj3) {
226: List list = new ArrayList(3);
227:
228: list.add(obj1);
229: list.add(obj2);
230: list.add(obj3);
231: return list;
232: }
233:
234: /**
235: * Create a list from passed objX parameters
236: * @return The resulting List
237: */
238: public static List toList(Object obj1, Object obj2, Object obj3,
239: Object obj4) {
240: List list = new ArrayList(4);
241:
242: list.add(obj1);
243: list.add(obj2);
244: list.add(obj3);
245: list.add(obj4);
246: return list;
247: }
248:
249: /**
250: * Create a list from passed objX parameters
251: * @return The resulting List
252: */
253: public static List toList(Object obj1, Object obj2, Object obj3,
254: Object obj4, Object obj5) {
255: List list = new ArrayList(5);
256:
257: list.add(obj1);
258: list.add(obj2);
259: list.add(obj3);
260: list.add(obj4);
261: list.add(obj5);
262: return list;
263: }
264:
265: /**
266: * Create a list from passed objX parameters
267: * @return The resulting List
268: */
269: public static List toList(Object obj1, Object obj2, Object obj3,
270: Object obj4, Object obj5, Object obj6) {
271: List list = new ArrayList(6);
272:
273: list.add(obj1);
274: list.add(obj2);
275: list.add(obj3);
276: list.add(obj4);
277: list.add(obj5);
278: list.add(obj6);
279: return list;
280: }
281:
282: public static List toList(Collection collection) {
283: if (collection == null)
284: return null;
285: if (collection instanceof List) {
286: return (List) collection;
287: } else {
288: return new ArrayList(collection);
289: }
290: }
291:
292: public static List toListArray(Object[] data) {
293: if (data == null) {
294: return null;
295: }
296: List list = new ArrayList(data.length);
297: for (int i = 0; i < data.length; i++) {
298: list.add(data[i]);
299: }
300: return list;
301: }
302:
303: /**
304: * Parse a locale string Locale object
305: * @param localeString The locale string (en_US)
306: * @return Locale The new Locale object or null if no valid locale can be interpreted
307: */
308: public static Locale parseLocale(String localeString) {
309: if (localeString == null || localeString.length() == 0) {
310: return null;
311: }
312:
313: Locale locale = null;
314: if (localeString.length() == 2) {
315: // two letter language code
316: locale = new Locale(localeString);
317: } else if (localeString.length() == 5) {
318: // positions 0-1 language, 3-4 are country
319: String language = localeString.substring(0, 2);
320: String country = localeString.substring(3, 5);
321: locale = new Locale(language, country);
322: } else if (localeString.length() > 6) {
323: // positions 0-1 language, 3-4 are country, 6 and on are special extensions
324: String language = localeString.substring(0, 2);
325: String country = localeString.substring(3, 5);
326: String extension = localeString.substring(6);
327: locale = new Locale(language, country, extension);
328: } else {
329: Debug
330: .logWarning(
331: "Do not know what to do with the localeString ["
332: + localeString
333: + "], should be length 2, 5, or greater than 6, returning null",
334: module);
335: }
336:
337: return locale;
338: }
339:
340: /** The input can be a String, Locale, or even null and a valid Locale will always be returned; if nothing else works, returns the default locale.
341: * @param localeObject An Object representing the locale
342: */
343: public static Locale ensureLocale(Object localeObject) {
344: if (localeObject != null && localeObject instanceof String) {
345: localeObject = UtilMisc.parseLocale((String) localeObject);
346: }
347: if (localeObject != null && localeObject instanceof Locale) {
348: return (Locale) localeObject;
349: } else {
350: return Locale.getDefault();
351: }
352: }
353:
354: public static List availableLocaleList = null;
355:
356: /** Returns a List of available locales sorted by display name */
357: public static List availableLocales() {
358: if (availableLocaleList == null) {
359: synchronized (UtilMisc.class) {
360: if (availableLocaleList == null) {
361: TreeMap localeMap = new TreeMap();
362: Locale[] locales = Locale.getAvailableLocales();
363: for (int i = 0; i < locales.length; i++) {
364: localeMap.put(locales[i].getDisplayName(),
365: locales[i]);
366: }
367: availableLocaleList = new LinkedList(localeMap
368: .values());
369: }
370: }
371: }
372: return availableLocaleList;
373: }
374:
375: /** This is meant to be very quick to create and use for small sized maps, perfect for how we usually use UtilMisc.toMap */
376: protected static class SimpleMap implements Map,
377: java.io.Serializable {
378: protected Map realMapIfNeeded = null;
379:
380: String[] names;
381: Object[] values;
382:
383: public SimpleMap() {
384: names = new String[0];
385: values = new Object[0];
386: }
387:
388: public SimpleMap(String name1, Object value1) {
389: names = new String[1];
390: values = new Object[1];
391: this .names[0] = name1;
392: this .values[0] = value1;
393: }
394:
395: public SimpleMap(String name1, Object value1, String name2,
396: Object value2) {
397: names = new String[2];
398: values = new Object[2];
399: this .names[0] = name1;
400: this .values[0] = value1;
401: this .names[1] = name2;
402: this .values[1] = value2;
403: }
404:
405: public SimpleMap(String name1, Object value1, String name2,
406: Object value2, String name3, Object value3) {
407: names = new String[3];
408: values = new Object[3];
409: this .names[0] = name1;
410: this .values[0] = value1;
411: this .names[1] = name2;
412: this .values[1] = value2;
413: this .names[2] = name3;
414: this .values[2] = value3;
415: }
416:
417: public SimpleMap(String name1, Object value1, String name2,
418: Object value2, String name3, Object value3,
419: String name4, Object value4) {
420: names = new String[4];
421: values = new Object[4];
422: this .names[0] = name1;
423: this .values[0] = value1;
424: this .names[1] = name2;
425: this .values[1] = value2;
426: this .names[2] = name3;
427: this .values[2] = value3;
428: this .names[3] = name4;
429: this .values[3] = value4;
430: }
431:
432: protected void makeRealMap() {
433: realMapIfNeeded = new HashMap();
434: for (int i = 0; i < names.length; i++) {
435: realMapIfNeeded.put(names[i], values[i]);
436: }
437: this .names = null;
438: this .values = null;
439: }
440:
441: public void clear() {
442: if (realMapIfNeeded != null) {
443: realMapIfNeeded.clear();
444: } else {
445: realMapIfNeeded = new HashMap();
446: names = null;
447: values = null;
448: }
449: }
450:
451: public boolean containsKey(Object obj) {
452: if (realMapIfNeeded != null) {
453: return realMapIfNeeded.containsKey(obj);
454: } else {
455: for (int i = 0; i < names.length; i++) {
456: if (obj == null && names[i] == null)
457: return true;
458: if (names[i] != null && names[i].equals(obj))
459: return true;
460: }
461: return false;
462: }
463: }
464:
465: public boolean containsValue(Object obj) {
466: if (realMapIfNeeded != null) {
467: return realMapIfNeeded.containsValue(obj);
468: } else {
469: for (int i = 0; i < names.length; i++) {
470: if (obj == null && values[i] == null)
471: return true;
472: if (values[i] != null && values[i].equals(obj))
473: return true;
474: }
475: return false;
476: }
477: }
478:
479: public java.util.Set entrySet() {
480: if (realMapIfNeeded != null) {
481: return realMapIfNeeded.entrySet();
482: } else {
483: this .makeRealMap();
484: return realMapIfNeeded.entrySet();
485: }
486: }
487:
488: public Object get(Object obj) {
489: if (realMapIfNeeded != null) {
490: return realMapIfNeeded.get(obj);
491: } else {
492: for (int i = 0; i < names.length; i++) {
493: if (obj == null && names[i] == null)
494: return values[i];
495: if (names[i] != null && names[i].equals(obj))
496: return values[i];
497: }
498: return null;
499: }
500: }
501:
502: public boolean isEmpty() {
503: if (realMapIfNeeded != null) {
504: return realMapIfNeeded.isEmpty();
505: } else {
506: if (this .names.length == 0)
507: return true;
508: return false;
509: }
510: }
511:
512: public java.util.Set keySet() {
513: if (realMapIfNeeded != null) {
514: return realMapIfNeeded.keySet();
515: } else {
516: this .makeRealMap();
517: return realMapIfNeeded.keySet();
518: }
519: }
520:
521: public Object put(Object obj, Object obj1) {
522: if (realMapIfNeeded != null) {
523: return realMapIfNeeded.put(obj, obj1);
524: } else {
525: this .makeRealMap();
526: return realMapIfNeeded.put(obj, obj1);
527: }
528: }
529:
530: public void putAll(java.util.Map map) {
531: if (realMapIfNeeded != null) {
532: realMapIfNeeded.putAll(map);
533: } else {
534: this .makeRealMap();
535: realMapIfNeeded.putAll(map);
536: }
537: }
538:
539: public Object remove(Object obj) {
540: if (realMapIfNeeded != null) {
541: return realMapIfNeeded.remove(obj);
542: } else {
543: this .makeRealMap();
544: return realMapIfNeeded.remove(obj);
545: }
546: }
547:
548: public int size() {
549: if (realMapIfNeeded != null) {
550: return realMapIfNeeded.size();
551: } else {
552: return this .names.length;
553: }
554: }
555:
556: public java.util.Collection values() {
557: if (realMapIfNeeded != null) {
558: return realMapIfNeeded.values();
559: } else {
560: this .makeRealMap();
561: return realMapIfNeeded.values();
562: }
563: }
564:
565: public String toString() {
566: if (realMapIfNeeded != null) {
567: return realMapIfNeeded.toString();
568: } else {
569: StringBuffer outString = new StringBuffer("{");
570: for (int i = 0; i < names.length; i++) {
571: if (i > 0)
572: outString.append(',');
573: outString.append('{');
574: outString.append(names[i]);
575: outString.append(',');
576: outString.append(values[i]);
577: outString.append('}');
578: }
579: outString.append('}');
580: return outString.toString();
581: }
582: }
583:
584: public int hashCode() {
585: if (realMapIfNeeded != null) {
586: return realMapIfNeeded.hashCode();
587: } else {
588: int hashCode = 0;
589: for (int i = 0; i < names.length; i++) {
590: //note that this calculation is done based on the calc specified in the Java java.util.Map interface
591: int tempNum = (names[i] == null ? 0 : names[i]
592: .hashCode())
593: ^ (values[i] == null ? 0 : values[i]
594: .hashCode());
595: hashCode += tempNum;
596: }
597: return hashCode;
598: }
599: }
600:
601: public boolean equals(Object obj) {
602: if (realMapIfNeeded != null) {
603: return realMapIfNeeded.equals(obj);
604: } else {
605: Map mapObj = (Map) obj;
606:
607: //first check the size
608: if (mapObj.size() != names.length)
609: return false;
610:
611: //okay, same size, now check each entry
612: for (int i = 0; i < names.length; i++) {
613: //first check the name
614: if (!mapObj.containsKey(names[i]))
615: return false;
616:
617: //if that passes, check the value
618: Object mapValue = mapObj.get(names[i]);
619: if (mapValue == null) {
620: if (values[i] != null)
621: return false;
622: } else {
623: if (!mapValue.equals(values[i]))
624: return false;
625: }
626: }
627:
628: return true;
629: }
630: }
631: }
632: }
|