如何将List <X>转换为另一个List <Y>

zhm*_*zhm 41 java transform list guava

我有两个对象列表; List<X>List<Y>.X并且Y是看起来像的对象:

public class X {
    String a;
    String b;
    String v;
    String w;
    String m;
    String n;
}

public class Y {
    String a;
    String b;
    List<A> aList;
}
public class A {
    String v;
    String w;
    List<B> bList;
}
public class B {
    String m;
    String n;
}
Run Code Online (Sandbox Code Playgroud)

如何转变List<X>List<Y>基于一个规则:
有些字段的值必须相等.
例如:
List<Y>,对于一个对象Y,字段a的值必须相等.
在Y的字段中List<A>,对于一个对象A,字段w的值必须相等.
在A的字段中List<B>,对于一个对象B,字段m的值必须相等,依此类推.

Guava有这个方法,Lists#transform,但我不知道如何转换.

还是其他任何方式?

Mis*_*ble 74

public static <F,T> List<T> transform(List<F> fromList,
                                      Function<? super F,? extends T> function
Run Code Online (Sandbox Code Playgroud)

您可能想要阅读Lists.transform()Function的API文档,但基本上转换的调用者提供了Function一个F将a 转换为a的对象T.

例如,如果你有一个List<Integer> intList和要创建List<String>使得后者的每一个元素包含该号码的英语表示(1变成"一"等),并必须将一个类中的访问诸如IntToEnglish然后

Function<Integer, String> intToEnglish = 
    new Function<Integer,String>() { 
        public String apply(Integer i) { return new IntToEnglish().english_number(i); }
    };

List<String> wordsList = Lists.transform(intList, intToEnglish);
Run Code Online (Sandbox Code Playgroud)

那转换.

您可以应用相同的模式来转换List<X>List<Y>

  • 这是一个有趣的问题:转换返回原始列表的*视图*,*仍然*链接到原始列表,而不是单独的新列表.即,如果从transform返回的列表中删除元素,它也将从原始列表中删除该元素.刚把我抓了出来,所以以为我会分享:) (4认同)
  • BE AWARE - Lists.transform()是懒散的!来自Guava JavaDoc:注意:序列化返回的列表是通过序列化fromList,其内容和函数来实现的 - 而不是通过序列化转换后的值.这可能会导致令人惊讶的行为,因此不建议序列化返回的列表.而是使用ImmutableList.copyOf(Collection)复制列表(例如),然后序列化副本.因此,与此类似的其他方法根本不实现序列化. (2认同)

bil*_*boc 10

用java lambda:

public static <K,V,Q extends K> List<V> transform( final List<Q> input, final java.util.function.Function<K,V> tfunc ) {
    if( null == input ) {
        return null;
    }
    return input.stream().map(tfunc).collect( Collectors.toList() );
}
Run Code Online (Sandbox Code Playgroud)

您只需要实现:java.util.function.Function


bla*_*mpe 6

这个怎么样?

import java.util.ArrayList;
import java.util.List;
import com.google.common.base.Function;
import com.google.common.collect.Lists;

public class GuavaTransform {
    public static void main(String[] args) {
        List<X> xList = new ArrayList<X>();
        xList.add(new X("a", "b", "v", "w", "m", "n"));
        xList.add(new X("a1", "b1", "v1", "w1", "m1", "n1"));
        for(X elem: xList) {
            System.out.println("An instance of X:"+ elem);
        }
        System.out.println();
        List<Y> yList = Lists.transform(xList, new TransformXY());
        for(Y elem: yList) {
            System.out.println("The corresponding instance of Y: \n"+elem);
        }
    }
}

class TransformXY implements Function<X, Y> {

    @Override
    public Y apply(X x) {
        List<B> bList = new ArrayList<B>();
        bList.add(new B(x.m, x.n));
        List<A> aList = new ArrayList<A>();
        aList.add(new A(x.v, x.w, bList));
        return new Y(x.a, x.b, aList);
    }
}

class X {
    String a;
    String b;
    String v;
    String w;
    String m;
    String n;
    X(String a, String b, String v, String w, String m, String n) {
        super();
        this.a = a;
        this.b = b;
        this.v = v;
        this.w = w;
        this.m = m;
        this.n = n;
    }
    public String toString() {
        StringBuilder sb = new StringBuilder();
        sb.append("(");
        sb.append(a+",");
        sb.append(b+",");
        sb.append(v+",");
        sb.append(w+",");
        sb.append(m+",");
        sb.append(n);
        sb.append(")");
        return sb.toString();
    }
}
class Y {
    String a;
    String b;
    List<A> aList;
    Y(String a, String b, List<A> aList) {
        super();
        this.a = a;
        this.b = b;
        this.aList = aList;
    }
    public String toString() {
        StringBuilder sb = new StringBuilder();
        sb.append(a+"\n");
        sb.append(b+"\n");
        for(A elem: aList) {
            sb.append(elem+"\n");
        }
        return sb.toString();
    } 
}
class A {
    String v;
    String w;
    List<B> bList;
    A(String v, String w, List<B> bList) {
        super();
        this.v = v;
        this.w = w;
        this.bList = bList;
    }
    public String toString() {
        StringBuilder sb = new StringBuilder();
        sb.append("--------"+v+"\n");
        sb.append("--------"+w+"\n");
        for(B elem: bList) {
            sb.append(elem+"\n");
        }
        return sb.toString();
    }

}
class B {
    String m;
    String n;
    B(String m, String n) {
        super();
        this.m = m;
        this.n = n;
    }
    public String toString() {
        StringBuilder sb = new StringBuilder();
        sb.append("----------------"+m+"\n");
        sb.append("----------------"+n+"\n");
        return sb.toString();
    }
}
Run Code Online (Sandbox Code Playgroud)

控制台输出:

An instance of X:(a,b,v,w,m,n)
An instance of X:(a1,b1,v1,w1,m1,n1)

The corresponding instance of Y: 
a
b
--------v
--------w
----------------m
----------------n



The corresponding instance of Y: 
a1
b1
--------v1
--------w1
----------------m1
----------------n1
Run Code Online (Sandbox Code Playgroud)


bar*_*man 5

与@Isaace 相同,但使用 lambda 语法(从这个例子中得到):

List<X> xList = new ArrayList<>();
List<Y> yList = xList
        .stream()
        .map(n -> someTransformFunc(n))
        .collect(Collectors.toList());
Run Code Online (Sandbox Code Playgroud)