JAL-653 JAL-1968 FeaturesFile now handles Jalview or GFF2 or GFF3
[jalview.git] / src / jalview / util / StringUtils.java
index 533e98b..ad1c0f7 100644 (file)
@@ -21,7 +21,9 @@
 package jalview.util;
 
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.List;
+import java.util.Map;
 import java.util.regex.Pattern;
 
 public class StringUtils
@@ -248,4 +250,121 @@ public class StringUtils
     }
     return "" + separator;
   }
+  
+  /**
+   * Parses the input line to a map of name / value(s) pairs. For example the
+   * line <br>
+   * Notes=Fe-S;Method=manual curation; source = Pfam; Notes = Metal <br>
+   * if parsed with delimiter=";" and separators {' ', '='} <br>
+   * would return a map with { Notes={Fe=S, Metal}, Method={manual curation},
+   * source={Pfam}} <br>
+   * Note the name/value strings are trimmed of leading / trailing spaces; the
+   * first separator encountered is used
+   * 
+   * @param line
+   * @param delimiter
+   *          the major delimiter between name-value pairs
+   * @param separators
+   *          one or more separators used between name and value
+   * @return the name-values map (which may be empty but never null)
+   */
+  public static Map<String, List<String>> parseNameValuePairs(String line,
+          String delimiter, char[] separators)
+  {
+    Map<String, List<String>> map = new HashMap<String, List<String>>();
+    if (line == null || line.trim().length() == 0)
+    {
+      return map;
+    }
+
+    for (String pair : line.trim().split(delimiter))
+    {
+      pair = pair.trim();
+      if (pair.length() == 0)
+      {
+        continue;
+      }
+
+      int sepPos = -1;
+      for (char sep : separators)
+      {
+        int pos = pair.indexOf(sep);
+        if (pos > -1 && (sepPos == -1 || pos < sepPos))
+        {
+          sepPos = pos;
+        }
+      }
+
+      if (sepPos == -1)
+      {
+        // no name=value detected
+        continue;
+      }
+
+      String key = pair.substring(0, sepPos).trim();
+      String value = pair.substring(sepPos + 1).trim();
+      if (value.length() > 0)
+      {
+        List<String> vals = map.get(key);
+        if (vals == null)
+        {
+          vals = new ArrayList<String>();
+          map.put(key, vals);
+        }
+        vals.add(value);
+      }
+    }
+    return map;
+  }
+
+  /**
+   * Converts a list to a string with a delimiter before each term except the
+   * first. Returns an empty string given a null or zero-length argument. This
+   * can be replaced with StringJoiner in Java 8.
+   * 
+   * @param terms
+   * @param delim
+   * @return
+   */
+  public static String listToDelimitedString(List<String> terms,
+          String delim)
+  {
+    StringBuilder sb = new StringBuilder(32);
+    if (terms != null && !terms.isEmpty())
+    {
+      boolean appended = false;
+      for (String term : terms)
+      {
+        if (appended)
+        {
+          sb.append(delim);
+        }
+        appended = true;
+        sb.append(term);
+      }
+    }
+    return sb.toString();
+  }
+
+  /**
+   * Convenience method to parse a string to an integer, returning 0 if the
+   * input is null or not a valid integer
+   * 
+   * @param s
+   * @return
+   */
+  public static int parseInt(String s)
+  {
+    int result = 0;
+    if (s != null && s.length() > 0)
+    {
+      try
+      {
+        result = Integer.parseInt(s);
+      } catch (NumberFormatException ex)
+      {
+      }
+    }
+    return result;
+  }
 }