RefUtils.java :  » Natural-Language-Processing » MinorThird » edu » cmu » minorthird » util » Java Open Source

Java Open Source » Natural Language Processing » MinorThird 
MinorThird » edu » cmu » minorthird » util » RefUtils.java
package edu.cmu.minorthird.util;

import java.lang.reflect.Method;

import org.apache.log4j.Logger;

/**
 * Utilities for reflection.
 */
public class RefUtils
{
  private static Logger log = Logger.getLogger(RefUtils.class);
  private static int LHS=0, RHS=1;

  static private String toGetter(String s)
  {
    return "get"+s.substring(0,1).toUpperCase()+s.substring(1);
  }

  static private String toSetter(String s)
  {
    return "set"+s.substring(0,1).toUpperCase()+s.substring(1);
  }

  /**
   * Creates an instance of class c, initialized with the string s.
   * String can be something like "true", "false", "1041", "13.56", or
   * the name of a class (for instance
   * "text.learn.SequentialLearner").
   */
  static private Object toObject(String s,Class<?> c)
  {
    if ((c==Boolean.class  || c==boolean.class) && s.equalsIgnoreCase("true")) return new Boolean(true);
    else if ((c==Boolean.class || c==boolean.class) && s.equalsIgnoreCase("false")) return new Boolean(false);
    else if (c==Integer.class || c==int.class) return new Integer(StringUtil.atoi(s));
    else if (c==Double.class || c==double.class) return new Double(StringUtil.atof(s));
    else try {
      return Class.forName(s).newInstance();
    } catch (Exception ex1) { 
      try {
        return Class.forName("edu.cmu.minorthird."+s).newInstance();
      } catch (Exception ex2) {
        try{
          int i = s.lastIndexOf('.');
          int len = s.length();
          String s2 = s.substring(0,i) + "$" + s.substring(i+1,len);
          return Class.forName("edu.cmu.minorthird."+s2).newInstance();
        } catch (Exception ex3){
          try {
            int i = s.lastIndexOf('.');
            int len = s.length();
            String s2 = s.substring(0,i) + "$" + s.substring(i+1,len);
            return Class.forName(s2).newInstance();
          } catch (Exception ex4){
            throw new IllegalArgumentException("can't create instance of '"+s+"' or 'edu.cmu.minorthird."+s+"'");
          }
        }
      }
    }
  }

  /**
   * Returns a modified copy of the object.  
   *
   * @param modifications a comma or semi-colon separated list of
   * strings of the form LHS=RHS, where RHS is something that can be
   * passed to toObject(), and LHS is a period-separated chain of
   * getters/setters, where only the last item is a setter.
   * <p>
   * Example:<br>
   * <code>RefUtils.modify(
   *           new StackedSequenceLearner(new MaxEntLearner(),1),<br>
   *           "params.historySize=1,params.futureSize=0")<br>
   * </code>
   * is the same as:
   * <code>
   * StackedSequenceLearner a = new StackedSequenceLearner(new MaxEntLearner(),1);<br>
   * a.getParams().setHistorySize(1);<br>
   * a.getParams().setFutureSize(0);<br>
   * </code>
   */
  public static Object modify(Object obj,String modifications)
  {
    String[] mods = modifications.split("[,;]\\s*");
    for (int i=0; i<mods.length; i++) {
      String[] sides = mods[i].split("=");
      if (sides.length!=2) {
        log.warn("Illegal modification (should be of the form x=y): "+mods[i]);
        continue;
      }
      String[] path = sides[LHS].split("\\.");
      Object objToChange=obj;
      try {
        for (int j=0; j<path.length-1; j++) {
          Method m = objToChange.getClass().getMethod(toGetter(path[j]),new Class[]{});
          objToChange = m.invoke(objToChange, new Object[]{});
        }
        // find a setter method m
        Method m = null; 
        Method ms[] = objToChange.getClass().getMethods();
        String setterName = toSetter(path[path.length-1]);
        for (int k=0; k<ms.length; k++) {
          if (setterName.equals(ms[k].getName())) {
            m = ms[k];
            break;
          }
        }
        if (m==null) log.warn("No setter defined for '"+path[path.length-1]+"'");
        else {
          Class<?>[] expectedClasses = m.getParameterTypes();
          Object rhs = toObject(sides[RHS], expectedClasses[0]);
          m.invoke(objToChange, new Object[]{rhs});
        }
      } catch (Exception ex) {
        log.warn("Can't execute modification '"+mods[i]+"': error was "+ex);
      }
    }
    return obj;
  }
}

java2s.com  | Contact Us | Privacy Policy
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.