Utils.java

  1. package com.gh.mygreen.xlsmapper.util;

  2. import java.lang.reflect.InvocationTargetException;
  3. import java.lang.reflect.Method;
  4. import java.util.ArrayList;
  5. import java.util.Arrays;
  6. import java.util.Collection;
  7. import java.util.Iterator;
  8. import java.util.LinkedHashSet;
  9. import java.util.LinkedList;
  10. import java.util.List;
  11. import java.util.Locale;
  12. import java.util.Map;
  13. import java.util.Optional;
  14. import java.util.Queue;
  15. import java.util.Set;

  16. import org.apache.poi.ss.usermodel.Sheet;

  17. import com.gh.mygreen.xlsmapper.BeanFactory;
  18. import com.gh.mygreen.xlsmapper.Configuration;
  19. import com.gh.mygreen.xlsmapper.XlsMapperException;
  20. import com.gh.mygreen.xlsmapper.annotation.XlsTrim;
  21. import com.gh.mygreen.xlsmapper.cellconverter.DefaultElementConverter;
  22. import com.gh.mygreen.xlsmapper.cellconverter.ElementConverter;
  23. import com.gh.mygreen.xlsmapper.fieldprocessor.ProcessCase;
  24. import com.gh.mygreen.xlsmapper.validation.SheetBindingErrors;


  25. /**
  26.  * ユーティリティクラス。
  27.  *
  28.  * @version 2.3
  29.  * @author T.TSUCHIE
  30.  * @author Naoki Takezoe
  31.  * @author Mitsuyoshi Hasegawa
  32.  *
  33.  */
  34. public class Utils {

  35.     @SuppressWarnings("rawtypes")
  36.     private static final ElementConverter ELEMENT_CONVERTER = new DefaultElementConverter();

  37.     /**
  38.      * コレクションの要素を指定した区切り文字で繋げて1つの文字列とする。
  39.      * @param col 処理対象のコレクション。
  40.      * @param separator 区切り文字。
  41.      * @param ignoreEmptyElement 空、nullの要素を無視するかどうか。
  42.      * @param trim トリムをするかどうか。
  43.      * @param elementConverter 要素を変換するクラス。
  44.      * @return 結合した文字列
  45.      */
  46.     @SuppressWarnings("rawtypes")
  47.     public static String join(final Collection<?> col, final String separator,
  48.             final boolean ignoreEmptyElement, final boolean trim, final ElementConverter elementConverter) {

  49.         final List<Object> list = new ArrayList<Object>();
  50.         for(Object element : col) {
  51.             if(element == null) {
  52.                 continue;
  53.             }

  54.             Object value = element;

  55.             if(element instanceof String) {
  56.                 String str = (String) element;
  57.                 if(ignoreEmptyElement && isEmpty(str)) {
  58.                     continue;

  59.                 } else if(trim) {
  60.                     value = str.trim();
  61.                 }

  62.             } else if(element instanceof Character && isEmpty(element.toString())) {
  63.                 String str = element.toString();
  64.                 if(ignoreEmptyElement && isEmpty(str)) {
  65.                     continue;

  66.                 } else if(trim) {
  67.                     value = str.trim().charAt(0);
  68.                 }

  69.             } else if(char.class.isAssignableFrom(element.getClass())) {
  70.                 String str = element.toString();
  71.                 if(ignoreEmptyElement && isEmpty(str)) {
  72.                     continue;

  73.                 } else if(trim) {
  74.                     value = str.trim().charAt(0);
  75.                 }
  76.             }

  77.             list.add(value);

  78.         }

  79.         return join(list, separator, elementConverter);

  80.     }

  81.     /**
  82.      * 配列の要素を指定した区切り文字で繋げて1つの文字列とする。
  83.      * @param arrays 結合対象の配列
  84.      * @param separator 区切り文字
  85.      * @return 結合した文字列
  86.      */
  87.     public static String join(final Object[] arrays, final String separator) {

  88.         return join(arrays, separator, ELEMENT_CONVERTER);

  89.     }

  90.     /**
  91.      * 配列の要素を指定した区切り文字で繋げて1つの文字列とする。
  92.      * @param arrays 結合対象の配列
  93.      * @param separator 区切り文字
  94.      * @param elementConverter 要素を変換するクラス。
  95.      * @return 結合した文字列
  96.      */
  97.     @SuppressWarnings({"rawtypes", "unchecked"})
  98.     public static String join(final Object[] arrays, final String separator, final ElementConverter elementConverter) {

  99.         if(arrays == null) {
  100.             return "";
  101.         }

  102.         final int len = arrays.length;
  103.         if(len == 0) {
  104.             return "";
  105.         }

  106.         StringBuilder sb = new StringBuilder();
  107.         for(int i=0; i < len; i++) {
  108.             final Object element = arrays[i];
  109.             sb.append(elementConverter.convertToString(element));

  110.             if(separator != null && (i < len-1)) {
  111.                 sb.append(separator);
  112.             }
  113.         }

  114.         return sb.toString();

  115.     }

  116.     /**
  117.      * Collectionの要素を指定した区切り文字で繋げて1つの文字列とする。
  118.      * @param col 結合対象のコレクション
  119.      * @param separator 区切り文字
  120.      * @return 結合した文字列
  121.      */
  122.     public static String join(final Collection<?> col, final String separator) {
  123.         return join(col, separator, ELEMENT_CONVERTER);
  124.     }

  125.     /**
  126.      * Collectionの要素を指定した区切り文字で繋げて1つの文字列とする。
  127.      * @param col 結合対象のコレクション
  128.      * @param separator 区切り文字
  129.      * @param elementConverter 要素を変換するクラス。
  130.      * @return 結合した文字列
  131.      */
  132.     @SuppressWarnings({"rawtypes", "unchecked"})
  133.     public static String join(final Collection<?> col, final String separator, final ElementConverter elementConverter) {

  134.         if(col == null) {
  135.             return "";
  136.         }

  137.         final int size = col.size();
  138.         if(size == 0) {
  139.             return "";
  140.         }

  141.         StringBuilder sb = new StringBuilder();
  142.         for(Iterator<?> itr = col.iterator(); itr.hasNext();) {
  143.             final Object element = itr.next();
  144.             String text = elementConverter.convertToString(element);
  145.             sb.append(text);

  146.             if(separator != null && itr.hasNext()) {
  147.                 sb.append(separator);
  148.             }
  149.         }

  150.         return sb.toString();

  151.     }

  152.     /**
  153.      * 先頭の文字を大文字にする。
  154.      * <pre>
  155.      * Utils.capitalize(null)  = null
  156.      * Utils.capitalize("")    = ""
  157.      * Utils.capitalize("cat") = "Cat"
  158.      * Utils.capitalize("cAt") = "CAt"
  159.      * </pre>
  160.      * @param str
  161.      * @return 引数がnull、空文字の場合、そのまま返す。
  162.      */
  163.     public static String capitalize(final String str) {
  164.         final int strLen;
  165.         if(str == null || (strLen = str.length()) == 0) {
  166.             return str;
  167.         }

  168.         return new StringBuilder(strLen)
  169.             .append(String.valueOf(str.charAt(0)).toUpperCase())
  170.             .append(str.substring(1))
  171.             .toString();
  172.     }

  173.     /**
  174.      * 先頭の文字を小文字にする。
  175.      * @param str 変換対象の文字
  176.      * @return 引数がnull、空文字の場合、そのまま返す。
  177.      */
  178.     public static String uncapitalize(final String str) {
  179.         final int strLen;
  180.         if(str == null || (strLen = str.length()) == 0) {
  181.             return str;
  182.         }

  183.         return new StringBuilder(strLen)
  184.             .append(String.valueOf(str.charAt(0)).toLowerCase())
  185.             .append(str.substring(1))
  186.             .toString();
  187.     }

  188.     /**
  189.      * システム設定に従いラベルを比較する。
  190.      * <p>正規表現や正規化を行い指定する。
  191.      *
  192.      * @since 1.1
  193.      * @param text1 セルのラベル
  194.      * @param text2 アノテーションに指定されているラベル。
  195.      *              {@literal /<ラベル>/}と指定する場合、正規表現による比較を行う。
  196.      * @param config システム設定
  197.      * @return true:ラベルが一致する。比較対象のラベルがnullの場合は、falseを返す。
  198.      */
  199.     public static boolean matches(final String text1, final String text2, final Configuration config){
  200.        
  201.         if(text1 == null || text2 == null) {
  202.             return false;
  203.         }
  204.        
  205.         if(config.isRegexLabelText() && text2.startsWith("/") && text2.endsWith("/")){
  206.             return normalize(text1, config).matches(text2.substring(1, text2.length() - 1));
  207.         } else {
  208.             return normalize(text1, config).equals(normalize(text2, config));
  209. //            return normalize(text1, config).equals(text2);
  210.         }
  211.     }

  212.     /**
  213.      * システム設定に従いラベルを正規化する。
  214.      * @since 1.1
  215.      * @param text セルのラベル
  216.      * @param config システム設定
  217.      * @return true:ラベルが一致する。
  218.      */
  219.     public static String normalize(final String text, final Configuration config){
  220.         if(text != null && config.isNormalizeLabelText()){
  221.             return text.trim().replaceAll("[\n\r]", "").replaceAll("[\t  ]+", " ");
  222.         }
  223.         return text;
  224.     }

  225.     /**
  226.      * 文字列が空文字か判定する。
  227.      * <p>文字数が1でかつ、{@literal \u0000}のときは、trueを判定する。</p>
  228.      * @param str 判定対象の文字
  229.      * @return trueの場合、空文字を判定する。
  230.      */
  231.     public static boolean isEmpty(final String str) {
  232.         if(str == null || str.isEmpty()) {
  233.             return true;
  234.         }

  235.         if(str.length() == 1) {
  236.             return str.charAt(0) == '\u0000';
  237.         }

  238.         return false;
  239.     }

  240.     /**
  241.      * 文字列が空文字でないか判定する。
  242.      * @param str 判定対象の文字
  243.      * @return
  244.      */
  245.     public static boolean isNotEmpty(final String str) {
  246.         return !isEmpty(str);
  247.     }

  248.     /**
  249.      * コレクションが空か判定する。
  250.      * @param collection
  251.      * @return nullまたはサイズが0のときにtrueを返す。
  252.      */
  253.     public static boolean isEmpty(final Collection<?> collection) {
  254.         if(collection == null || collection.isEmpty()) {
  255.             return true;
  256.         }

  257.         return false;
  258.     }

  259.     public static boolean isNotEmpty(final Collection<?> collection) {
  260.         return !isEmpty(collection);
  261.     }
  262.    
  263.     /**
  264.      * Mapが空か判定する。
  265.      * @param map
  266.      * @return nullまたはサイズが0のときにtrueを返す。
  267.      */
  268.     public static boolean isEmpty(final Map<?, ?> map) {
  269.         if(map == null || map.isEmpty()) {
  270.             return true;
  271.         }

  272.         return false;
  273.     }

  274.     public static boolean isNotEmpty(final Map<?, ?> map) {
  275.         return !isEmpty(map);
  276.     }

  277.     /**
  278.      * 配列がが空か判定する。
  279.      * @param arrays
  280.      * @return nullまたは、配列のサイズが0のときにtrueを返す。
  281.      */
  282.     public static boolean isEmpty(final Object[] arrays) {
  283.         if(arrays == null || arrays.length == 0) {
  284.             return true;
  285.         }

  286.         return false;
  287.     }

  288.     /**
  289.      * 配列が空でないか判定する
  290.      * @param arrays
  291.      * @return
  292.      */
  293.     public static boolean isNotEmpty(final Object[] arrays) {
  294.         return !isEmpty(arrays);
  295.     }
  296.    
  297.     /**
  298.      * オブジェクトの比較を行う。
  299.      * <p>値がnullの場合を考慮する。
  300.      * @param obj1
  301.      * @param obj2
  302.      * @return
  303.      */
  304.     public static boolean equals(final Object obj1, final Object obj2) {

  305.         if(obj1 == null && obj2 == null) {
  306.             return true;
  307.         }

  308.         if(obj1 == null) {
  309.             return false;
  310.         }

  311.         if(obj2 == null) {
  312.             return false;
  313.         }

  314.         return obj1.equals(obj2);

  315.     }

  316.     public static boolean notEquals(final Object obj1, final Object obj2) {
  317.         return !equals(obj1, obj2);
  318.     }

  319.     /**
  320.      * オブジェクトを文字列に変換する。
  321.      * <p>nullの場合、文字列として "null"を返す。
  322.      * <p>単純に、{@link Object#toString()}を呼び出す。
  323.      * @param value
  324.      * @return
  325.      */
  326.     public static String convertToString(final Object value) {

  327.         if(value == null) {
  328.             return "null";
  329.         }

  330.         return value.toString();

  331.     }

  332.     /**
  333.      * アノテーションの属性trimに従い、文字列をトリムする。
  334.      * @param value トリム対象の文字
  335.      * @param trimAnno トリムのアノテーション
  336.      * @return トリミングした結果。
  337.      */
  338.     public static String trim(final String value, final Optional<XlsTrim> trimAnno) {

  339.         if(!trimAnno.isPresent() || value == null) {
  340.             return value;
  341.         }

  342.         return value.trim();

  343.     }

  344.     /**
  345.      * 文字列をトリムする。
  346.      * @param value トリム対象の文字
  347.      * @param trimmed トリムするかどうか。
  348.      * @return トリミングした結果。
  349.      */
  350.     public static String trim(final String value, final boolean trimmed) {
  351.         if(!trimmed || value == null) {
  352.             return value;
  353.         }

  354.         return value.trim();

  355.     }
  356.    
  357.     /**
  358.      * 文字列をbooleanに変換します。
  359.      *
  360.      * @since 2.3
  361.      * @param value 変換対象の値。
  362.      * @param defaultValue 変換対象がnull or 空文字の時のデフォルト値。
  363.      * @return 引数がnullのとき、falseを返します。
  364.      */
  365.     public static boolean toBoolean(final String value, final boolean defaultValue) {
  366.         String text = trim(value, true);
  367.         if(isEmpty(text)) {
  368.             return defaultValue;
  369.         }
  370.        
  371.         return Boolean.valueOf(text.toLowerCase());
  372.     }

  373.     /**
  374.      * PostProcessなどのメソッドを実行する。
  375.      * <p>メソッドの引数が既知のものであれば、インスタンスを設定する。
  376.      *
  377.      * @param processObj 実行対象の処理が埋め込まれているオブジェクト。
  378.      * @param method 実行対象のメソッド情報
  379.      * @param beanObj 処理対象のBeanオブジェクト。
  380.      * @param sheet シート情報
  381.      * @param config 共通設定
  382.      * @param errors エラー情報
  383.      * @param processCase 処理ケース
  384.      * @throws XlsMapperException
  385.      */
  386.     public static void invokeNeedProcessMethod(final Object processObj, final Method method, final Object beanObj,
  387.             final Sheet sheet, final Configuration config, final SheetBindingErrors<?> errors, final ProcessCase processCase)
  388.                     throws XlsMapperException {

  389.         final Class<?>[] paramTypes = method.getParameterTypes();
  390.         final Object[] paramValues =  new Object[paramTypes.length];

  391.         for(int i=0; i < paramTypes.length; i++) {
  392.             if(Sheet.class.isAssignableFrom(paramTypes[i])) {
  393.                 paramValues[i] = sheet;

  394.             } else if(Configuration.class.isAssignableFrom(paramTypes[i])) {
  395.                 paramValues[i] = config;

  396.             } else if(SheetBindingErrors.class.isAssignableFrom(paramTypes[i])) {
  397.                 paramValues[i] = errors;

  398.             } else if(paramTypes[i].isAssignableFrom(beanObj.getClass())) {
  399.                 paramValues[i] = beanObj;

  400.             } else if(ProcessCase.class.equals(paramTypes[i])) {
  401.                 paramValues[i] = processCase;

  402.             } else if(paramTypes[i].equals(Object.class)) {
  403.                 paramValues[i] = beanObj;

  404.             } else {
  405.                 paramValues[i] = null;
  406.             }
  407.         }

  408.         try {
  409.             method.setAccessible(true);
  410.             method.invoke(processObj, paramValues);
  411.         } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
  412.             Throwable t = e.getCause() == null ? e : e.getCause();
  413.             throw new XlsMapperException(
  414.                     String.format("fail execute method '%s#%s'.", processObj.getClass().getName(), method.getName()),
  415.                     t);
  416.         }
  417.     }

  418.     /**
  419.      * 文字列形式のロケールをオブジェクトに変換する。
  420.      * <p>アンダーバーで区切った'ja_JP'を分解して、Localeに渡す。
  421.      * @param str
  422.      * @return 引数が空の時はデフォルトロケールを返す。
  423.      */
  424.     public static Locale getLocale(final String str) {

  425.         if(isEmpty(str)) {
  426.             return Locale.getDefault();
  427.         }

  428.         if(!str.contains("_")) {
  429.             return new Locale(str);
  430.         }

  431.         final String[] split = str.split("_");
  432.         if(split.length == 2) {
  433.             return new Locale(split[0], split[1]);

  434.         } else {
  435.             return new Locale(split[0], split[1], split[2]);
  436.         }

  437.     }

  438.     /**
  439.      * エスケープ文字を除去した文字列を取得する。
  440.      * @param str
  441.      * @param escapeChar
  442.      * @return
  443.      */
  444.     public static String removeEscapeChar(final String str, final char escapeChar) {

  445.         if(str == null || str.isEmpty()) {
  446.             return str;
  447.         }

  448.         final String escapeStr = String.valueOf(escapeChar);
  449.         StringBuilder sb = new StringBuilder();

  450.         LinkedList<String> stack = new LinkedList<String>();

  451.         final int length = str.length();
  452.         for(int i=0; i < length; i++) {
  453.             final char c = str.charAt(i);

  454.             if(StackUtils.equalsTopElement(stack, escapeStr)) {
  455.                 // スタックの一番上がエスケープ文字の場合
  456.                 StackUtils.popup(stack);
  457.                 sb.append(c);

  458.             } else if(c == escapeChar) {
  459.                 // スタックに積む
  460.                 stack.push(String.valueOf(c));

  461.             } else {
  462.                 sb.append(c);
  463.             }

  464.         }

  465.         if(!stack.isEmpty()) {
  466.             sb.append(StackUtils.popupAndConcat(stack));
  467.         }

  468.         return sb.toString();

  469.     }

  470.     /**
  471.      * Listのインスタンスを他のCollectionのインスタンスに変換する。
  472.      * <p>ただし、変換先のクラスタイプがインタフェースの場合は変換しない。
  473.      * <p>変換元のクラスと変換先のクラスが同じ場合は、変換しない。
  474.      *
  475.      * @since 1.0
  476.      * @param list 変換元のListのインスタンス
  477.      * @param toClass 変換先のCollectionのクラス
  478.      * @param beanFactory てインスタンスを生成するファクトリクラス。
  479.      * @return 変換したコレクションのインスタンス
  480.      */
  481.     @SuppressWarnings({"rawtypes", "unchecked"})
  482.     public static Collection convertListToCollection(final List list, final Class<Collection> toClass,
  483.             final BeanFactory<Class<?>, Object> beanFactory) {

  484.         if(list.getClass().equals(toClass)) {
  485.             return list;
  486.         }

  487.         if(toClass.isInterface()) {
  488.             if(List.class.isAssignableFrom(toClass)) {
  489.                 // 変換先がListの実態の場合はそのまま。
  490.                 return list;

  491.             } else if(Set.class.isAssignableFrom(toClass)) {

  492.                 Collection value = (Collection) beanFactory.create(LinkedHashSet.class);
  493.                 value.addAll(list);
  494.                 return value;

  495.             } else if(Queue.class.isAssignableFrom(toClass)) {

  496.                 Collection value = (Collection) beanFactory.create(LinkedList.class);
  497.                 value.addAll(list);
  498.                 return value;

  499.             } else if(Collection.class.isAssignableFrom(toClass)) {
  500.                 Collection value = (Collection) beanFactory.create(ArrayList.class);
  501.                 value.addAll(list);
  502.                 return value;

  503.             } else {
  504.                 throw new IllegalArgumentException("not support class type:" + toClass.getName());
  505.             }

  506.         }

  507.         Collection value = (Collection) beanFactory.create(toClass);
  508.         value.addAll(list);

  509.         return value;

  510.     }

  511.     /**
  512.      * CollectionのインスタンスをListに変換する。
  513.      *
  514.      * @since 1.0
  515.      * @param collection 変換元のCollectionのインスタンス。
  516.      * @return 変換したListのインスタンス。
  517.      */
  518.     public static <T> List<T> convertCollectionToList(final Collection<T> collection) {

  519.         if(List.class.isAssignableFrom(collection.getClass())) {
  520.             return (List<T>)collection;
  521.         }

  522.         return new ArrayList<>(collection);

  523.     }

  524.     /**
  525.      * リストに要素のインデックスを指定して追加します。
  526.      * <p>リストのサイズが足りない場合は、サイズを自動的に変更します。</p>
  527.      * @since 2.0
  528.      * @param list リスト
  529.      * @param element 追加する要素。値はnullでもよい。
  530.      * @param index 追加する要素のインデックス番号(0以上)
  531.      * @throws IllegalArgumentException {@literal list == null.}
  532.      * @throws IllegalArgumentException {@literal index < 0.}
  533.      */
  534.     public static <P> void addListWithIndex(final List<P> list, final P element, final int index) {
  535.         ArgUtils.notNull(list, "list");
  536.         ArgUtils.notMin(index, 0, "index");

  537.         final int listSize = list.size();
  538.         if(listSize < index) {
  539.             // 足りない場合は、要素を追加する。
  540.             final int lackSize = index - listSize;
  541.             for(int i=0; i < lackSize; i++) {
  542.                 list.add(null);
  543.             }
  544.             list.add(element);

  545.         } else if(listSize == index) {
  546.             // 最後の要素に追加する
  547.             list.add(element);

  548.         } else {
  549.             // リストのサイズが足りている場合
  550.             list.set(index, element);
  551.         }

  552.     }

  553.     /**
  554.      * プリミティブ型のデフォルト値を取得します。
  555.      * @param type 変換対象のクラスタイプ。
  556.      * @return 対応していない型の場合は、nullを返します。
  557.      * @throws IllegalArgumentException {@literal type is null.}
  558.      */
  559.     public static Object getPrimitiveDefaultValue(final Class<?> type) {
  560.         ArgUtils.notNull(type, "type");

  561.         if(!type.isPrimitive()) {
  562.             return null;
  563.         }

  564.         if(type.equals(boolean.class)) {
  565.             return false;

  566.         } else if(type.equals(char.class)) {
  567.             return '\u0000';

  568.         } else if(type.equals(byte.class)) {
  569.             return (byte)0;

  570.         } else if(type.equals(short.class)) {
  571.             return (short)0;

  572.         } else if(type.equals(int.class)) {
  573.             return 0;

  574.         } else if(type.equals(long.class)) {
  575.             return 0l;

  576.         } else if(type.equals(float.class)) {
  577.             return 0.0f;

  578.         } else if(type.equals(double.class)) {
  579.             return 0.0d;

  580.         }

  581.         return null;
  582.     }

  583.     /**
  584.      * 配列を{@link List}に変換します。
  585.      * プリミティブ型の配列をを考慮して処理します。
  586.      * @param object 変換対象の配列
  587.      * @param componentType 配列の要素のタイプ
  588.      * @return 配列がnullの場合は、空のリストに変換します。
  589.      * @throws IllegalArgumentException {@literal arrayが配列でない場合。componentTypeがサポートしていないプリミティブ型の場合。}
  590.      */
  591.     public static List<Object> asList(final Object object, final Class<?> componentType) {
  592.         ArgUtils.notNull(componentType, "componentType");

  593.         if(object == null) {
  594.             return new ArrayList<>();
  595.         }

  596.         if(!object.getClass().isArray()) {
  597.             throw new IllegalArgumentException(String.format("args0 is not arrays : %s.", object.getClass().getName()));
  598.         }

  599.         if(!componentType.isPrimitive()) {
  600.             return Arrays.asList((Object[])object);
  601.         }

  602.         if(componentType.equals(boolean.class)) {
  603.             boolean[] array = (boolean[])object;
  604.             List<Object> list = new ArrayList<>(array.length);
  605.             for(boolean v : array) {
  606.                 list.add(v);
  607.             }
  608.             return list;

  609.         } else if(componentType.equals(char.class)) {
  610.             char[] array = (char[])object;
  611.             List<Object> list = new ArrayList<>(array.length);
  612.             for(char v : array) {
  613.                 list.add(v);
  614.             }
  615.             return list;

  616.         } else if(componentType.equals(byte.class)) {
  617.             byte[] array = (byte[])object;
  618.             List<Object> list = new ArrayList<>(array.length);
  619.             for(byte v : array) {
  620.                 list.add(v);
  621.             }
  622.             return list;

  623.         } else if(componentType.equals(short.class)) {
  624.             short[] array = (short[])object;
  625.             List<Object> list = new ArrayList<>(array.length);
  626.             for(short v : array) {
  627.                 list.add(v);
  628.             }
  629.             return list;

  630.         } else if(componentType.equals(int.class)) {
  631.             int[] array = (int[])object;
  632.             List<Object> list = new ArrayList<>(array.length);
  633.             for(int v : array) {
  634.                 list.add(v);
  635.             }
  636.             return list;

  637.         } else if(componentType.equals(long.class)) {
  638.             long[] array = (long[])object;
  639.             List<Object> list = new ArrayList<>(array.length);
  640.             for(long v : array) {
  641.                 list.add(v);
  642.             }
  643.             return list;

  644.         } else if(componentType.equals(float.class)) {
  645.             float[] array = (float[])object;
  646.             List<Object> list = new ArrayList<>(array.length);
  647.             for(float v : array) {
  648.                 list.add(v);
  649.             }
  650.             return list;

  651.         } else if(componentType.equals(double.class)) {
  652.             double[] array = (double[])object;
  653.             List<Object> list = new ArrayList<>(array.length);
  654.             for(double v : array) {
  655.                 list.add(v);
  656.             }
  657.             return list;

  658.         }

  659.         throw new IllegalArgumentException(String.format("not support primitive type : %s.", componentType.getName()));

  660.     }

  661.     /**
  662.      * コレクションを配列に変換する。
  663.      * @param collection 変換対象のコレクション。
  664.      * @return 変換した配列。
  665.      * @throws IllegalArgumentException {@literal collection is null.}
  666.      */
  667.     public static int[] toArray(final Collection<Integer> collection) {
  668.         ArgUtils.notNull(collection, "collection");

  669.         final int size = collection.size();
  670.         final int[] array = new int[size];

  671.         int i=0;
  672.         for(Integer value : collection) {
  673.             array[i] = value;
  674.             i++;
  675.         }

  676.         return array;
  677.     }

  678.     /**
  679.      * 配列のサイズを取得します。
  680.      * プリミティブ型の配列をを考慮して処理します。
  681.      * @param object 取得対象の配列
  682.      * @param componentType 配列の要素のタイプ
  683.      * @return 配列がnullの場合は、0を返します。
  684.      * @throws IllegalArgumentException {@literal arrayが配列でない場合。componentTypeがサポートしていないプリミティブ型の場合。}
  685.      */
  686.     public static int getArraySize(final Object object, final Class<?> componentType) {

  687.         ArgUtils.notNull(componentType, "componentType");

  688.         if(object == null) {
  689.             return 0;
  690.         }

  691.         if(!object.getClass().isArray()) {
  692.             throw new IllegalArgumentException(String.format("args0 is not arrays : %s.", object.getClass().getName()));
  693.         }

  694.         if(!componentType.isPrimitive()) {
  695.             return ((Object[])object).length;
  696.         }

  697.         if(componentType.equals(boolean.class)) {
  698.             return ((boolean[]) object).length;

  699.         } else if(componentType.equals(char.class)) {
  700.             return ((char[]) object).length;

  701.         } else if(componentType.equals(byte.class)) {
  702.             return ((byte[]) object).length;

  703.         } else if(componentType.equals(short.class)) {
  704.             return ((short[]) object).length;

  705.         } else if(componentType.equals(int.class)) {
  706.             return ((int[]) object).length;

  707.         } else if(componentType.equals(long.class)) {
  708.             return ((long[]) object).length;

  709.         } else if(componentType.equals(float.class)) {
  710.             return ((byte[]) object).length;

  711.         } else if(componentType.equals(double.class)) {
  712.             return ((byte[]) object).length;

  713.         }

  714.         throw new IllegalArgumentException(String.format("not support primitive type : %s.", componentType.getName()));
  715.     }

  716.     /**
  717.      * 文字列配列の結合
  718.      * @param array1
  719.      * @param array2
  720.      * @return 結合した配列。引数のどちらからnullの場合は、cloneした配列を返します。
  721.      */
  722.     public static String[] concat(final String[] array1, final String[] array2) {

  723.         if(array1 == null || array1.length == 0) {
  724.             return clone(array2);

  725.         } else if(array2 == null || array2.length == 0) {
  726.             return clone(array1);
  727.         }

  728.         final String[] joinedArray = new String[array1.length + array2.length];
  729.         System.arraycopy(array1, 0, joinedArray, 0, array1.length);
  730.         System.arraycopy(array2, 0, joinedArray, array1.length, array2.length);
  731.         return joinedArray;

  732.     }

  733.     /**
  734.      * 文字列の配列をクローンします。
  735.      * @param array クローン対象の配列
  736.      * @return クローンした配列。引数がnullの場合は、nullを返します。
  737.      */
  738.     public static String[] clone(final String[] array) {
  739.         if (array == null) {
  740.             return null;
  741.         }
  742.         return array.clone();
  743.     }

  744.     /**
  745.      * 読み込み処理のケースか判定する。
  746.      * <p>ケースが指定されていないときは、該当すると判定する。</p>
  747.      * @since 2.0
  748.      * @param cases 判定対象のケース
  749.      * @return trueのとき、読み込み対象と判定する。
  750.      */
  751.     public static boolean isLoadCase(final ProcessCase[] cases) {

  752.         if(cases == null || cases.length == 0) {
  753.             return true;
  754.         }

  755.         for(ProcessCase pc : cases) {
  756.             if(pc == ProcessCase.Load) {
  757.                 return true;
  758.             }
  759.         }

  760.         return false;

  761.     }

  762.     /**
  763.      * 書き込み処理のケースか判定する。
  764.      * <p>ケースが指定されていないときは、該当すると判定する。</p>
  765.      * @since 2.0
  766.      * @param cases 判定対象のケース
  767.      * @return trueのとき、書き込み対象と判定する。
  768.      */
  769.     public static boolean isSaveCase(final ProcessCase[] cases) {

  770.         if(cases == null || cases.length == 0) {
  771.             return true;
  772.         }

  773.         for(ProcessCase pc : cases) {
  774.             if(pc == ProcessCase.Save) {
  775.                 return true;
  776.             }
  777.         }

  778.         return false;

  779.     }

  780.     /**
  781.      * 現在の処理ケースが該当するか判定する。
  782.      * <p>ケースが指定されていないときは、該当すると判定する。</p>
  783.      * @param currentCase 現在の処理ケース
  784.      * @param cases 判定対象のケース
  785.      * @return trueのとき判定対象。
  786.      * @throws IllegalArgumentException {@code currentCase is null.}
  787.      */
  788.     public static boolean isProcessCase(final ProcessCase currentCase, ProcessCase[] cases) {

  789.         ArgUtils.notNull(currentCase, "currentCase");

  790.         if(currentCase == ProcessCase.Load) {
  791.             return isLoadCase(cases);
  792.         } else if(currentCase == ProcessCase.Save) {
  793.             return isSaveCase(cases);
  794.         } else {
  795.             throw new IllegalArgumentException("currentCase is not support:" + currentCase);
  796.         }

  797.     }


  798. }