Java:使用泛型进行字符串解析以提高干燥度

Java:使用泛型进行字符串解析以提高干燥度,java,generics,Java,Generics,假设我需要解析以空格分隔的数字列表,其中有些列表包含整数,有些列表包含双精度。概括以下函数以减少重复的好方法是什么?我想这可能是泛型的一个很好的用例 public static ArrayList<Integer> stringToIntList(String str) { String[] strs = str.split("\\s"); ArrayList<Integer> output = new ArrayList<Integer>()

假设我需要解析以空格分隔的数字列表,其中有些列表包含整数,有些列表包含双精度。概括以下函数以减少重复的好方法是什么?我想这可能是泛型的一个很好的用例

public static ArrayList<Integer> stringToIntList(String str)
{
    String[] strs = str.split("\\s");
    ArrayList<Integer> output = new ArrayList<Integer>();
​
​
    for (String val : strs)
    {
        output.add(Integer.parseInt(val));
    }
​
    return output;
}
​
public static ArrayList<Double> stringToDoubleList(String str)
{
    String[] strs = str.split("\\s");
    ArrayList<Double> output = new ArrayList<Double>();
​
​
    for (String val : strs)
    {
        output.add(Double.parseDouble(val));
    }
​
    return output;
}
publicstaticarrayliststringtointlist(stringstr)
{
字符串[]strs=str.split(\\s”);
ArrayList输出=新的ArrayList();
​
​
for(字符串val:strs)
{
add(Integer.parseInt(val));
}
​
返回输出;
}
​
公共静态ArrayList stringToDoubleList(字符串str)
{
字符串[]strs=str.split(\\s”);
ArrayList输出=新的ArrayList();
​
​
for(字符串val:strs)
{
add(Double.parseDouble(val));
}
​
返回输出;
}

如果您有某种函数(例如or)接受
字符串并返回所需类型,则可以使用泛型执行此操作

static <T> ArrayList<T> stringToList(
    String str, Function<? super String, ? extends T> fn) {
  String[] strs = str.split("\\s");
  ArrayList<T> output = new ArrayList<>();
  for (String val : strs)
  {
      output.add(fn.apply(val));
  }
  return output;
 }
静态数组列表stringToList(

字符串str,函数使用Java 8,它可以非常简洁:

static <T> List<T> convertToList(
        String string, Function<String, T> function) {
    return Pattern.compile("\\s").splitAsStream(string)
            .map(function).collect(Collectors.toList());
}

public static void main(String[] args) {
    String s = "3 4";
    System.out.println(convertToList(s,Double::parseDouble)); // [3.0, 4.0]
    System.out.println(convertToList(s,Integer::parseInt)); // [3, 4]
}
静态列表转换器列表(
字符串(字符串、函数){
返回模式.compile(“\\s”).splitAsStream(字符串)
.map(function).collect(Collectors.toList());
}
公共静态void main(字符串[]args){
字符串s=“3 4”;
System.out.println(convertToList(s,Double::parseDouble));//[3.0,4.0]
System.out.println(convertToList(s,Integer::parseInt));//[3,4]
}

当模式不变时,您也可以将其设置为常量。

当我尝试此操作时,我收到一个错误消息,该函数返回的是
列表
,而不是
列表
。我是否需要在那里进行强制转换或其他操作?@evan058如何调用它?您需要传递一个返回T的函数,但如果T是我正在使用的对象,您将得到列表telliJ和IDE抛出了这个错误。我刚刚定义了这个函数,它说:不兼容的类型:必需的:
List
;找到的
List
啊,你需要做
Collectors.toList()
,而不是
Collectors.toList()
,即使在我试图运行
ArrayList dubTimes=convertToList的时候(times,Double::parseDouble)
我得到一个错误“方法引用中的返回类型不正确,无法将Double转换为T”。Andy Turner的答案适用于这种方法调用