如何转置List

发布于 2024-09-04 03:10:27 字数 231 浏览 3 评论 0原文

我有一个以下 ArrayList,

[Title,Data1,Data2,Data3]
[A,2,3,4]
[B,3,5,7]

我想像这样转换这个,

[Title,A,B]
[Data1,2,3]
[Data2,3,5]
[Data3,4,7]

我对这种方法有点困惑。任何提示将不胜感激。

谢谢。

I have a following ArrayList,

[Title,Data1,Data2,Data3]
[A,2,3,4]
[B,3,5,7]

And I would like to convert this one like this,

[Title,A,B]
[Data1,2,3]
[Data2,3,5]
[Data3,4,7]

I'm bit confused with the approach. Any hint would be much appreciated.

Thanks.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(12

镜花水月 2024-09-11 03:10:27

这称为转置。以下代码段满足您的需要:

import java.util.*;
public class ListTranspose {
    public static void main(String[] args) {
        Object[][] data = {
            { "Title", "Data1", "Data2", "Data3" },
            { "A", 2, 3, 4 },
            { "B", 3, 5, 7 },
        };
        List<List<Object>> table = new ArrayList<List<Object>>();
        for (Object[] row : data) {
            table.add(Arrays.asList(row));
        }
        System.out.println(table); //  [[Title, Data1, Data2, Data3],
                                   //   [A, 2, 3, 4],
                                   //   [B, 3, 5, 7]]"
        table = transpose(table);
        System.out.println(table); //  [[Title, A, B],
                                   //   [Data1, 2, 3],
                                   //   [Data2, 3, 5],
                                   //   [Data3, 4, 7]]
    }
    static <T> List<List<T>> transpose(List<List<T>> table) {
        List<List<T>> ret = new ArrayList<List<T>>();
        final int N = table.get(0).size();
        for (int i = 0; i < N; i++) {
            List<T> col = new ArrayList<T>();
            for (List<T> row : table) {
                col.add(row.get(i));
            }
            ret.add(col);
        }
        return ret;
    }
}

另请参阅

This is called transposition. The following snippet does what you need:

import java.util.*;
public class ListTranspose {
    public static void main(String[] args) {
        Object[][] data = {
            { "Title", "Data1", "Data2", "Data3" },
            { "A", 2, 3, 4 },
            { "B", 3, 5, 7 },
        };
        List<List<Object>> table = new ArrayList<List<Object>>();
        for (Object[] row : data) {
            table.add(Arrays.asList(row));
        }
        System.out.println(table); //  [[Title, Data1, Data2, Data3],
                                   //   [A, 2, 3, 4],
                                   //   [B, 3, 5, 7]]"
        table = transpose(table);
        System.out.println(table); //  [[Title, A, B],
                                   //   [Data1, 2, 3],
                                   //   [Data2, 3, 5],
                                   //   [Data3, 4, 7]]
    }
    static <T> List<List<T>> transpose(List<List<T>> table) {
        List<List<T>> ret = new ArrayList<List<T>>();
        final int N = table.get(0).size();
        for (int i = 0; i < N; i++) {
            List<T> col = new ArrayList<T>();
            for (List<T> row : table) {
                col.add(row.get(i));
            }
            ret.add(col);
        }
        return ret;
    }
}

See also

清浅ˋ旧时光 2024-09-11 03:10:27

这是我的解决方案。感谢@jpaugh 的代码。希望这对您有帮助。^_^

public static <T> List<List<T>> transpose(List<List<T>> list) {
   final int N = list.stream().mapToInt(l -> l.size()).max().orElse(-1);
   List<Iterator<T>> iterList = list.stream().map(it->it.iterator()).collect(Collectors.toList());
   return IntStream.range(0, N)
       .mapToObj(n -> iterList.stream()
       .filter(it -> it.hasNext())
       .map(m -> m.next())
       .collect(Collectors.toList()))
   .collect(Collectors.toList());
}

Here is my solution.Thanks to @jpaugh's code.I hope this will help you.^_^

public static <T> List<List<T>> transpose(List<List<T>> list) {
   final int N = list.stream().mapToInt(l -> l.size()).max().orElse(-1);
   List<Iterator<T>> iterList = list.stream().map(it->it.iterator()).collect(Collectors.toList());
   return IntStream.range(0, N)
       .mapToObj(n -> iterList.stream()
       .filter(it -> it.hasNext())
       .map(m -> m.next())
       .collect(Collectors.toList()))
   .collect(Collectors.toList());
}
寒尘 2024-09-11 03:10:27

这不是一种快速的方法,也不是最干净的方法,而是更多 kotlin 风格的代码。

fun <T> List<List<T>>.transpose(): List<List<T>> {
    val result = (first().indices).map { mutableListOf<T>() }.toMutableList()
    forEach { list -> result.zip(list).forEach { it.first.add(it.second) } }
    return result
}

第一行创建一个 M 大小的“结果”列表(对于 NxM 原始矩阵),而第二行 =>

  1. 迭代第一个(每个列表大小为 m)中的所有列表“a”,
  2. 将 a 的第 i 个项目附加到结果中的第 i 个列表。

Not a fast way, neither the cleanest one, but more of kotlin-ish code.

fun <T> List<List<T>>.transpose(): List<List<T>> {
    val result = (first().indices).map { mutableListOf<T>() }.toMutableList()
    forEach { list -> result.zip(list).forEach { it.first.add(it.second) } }
    return result
}

the first line creates a M size 'result' list (for NxM original matrix), while the second line =>

  1. iterates through all the lists 'a' in first (each list size m)
  2. append i-th item of a to the i-th list in result.
赏烟花じ飞满天 2024-09-11 03:10:27

这称为转置操作。代码示例位于此处,但需要进行重大修改因为你有一个数组的 ArrayList (我从你的问题中推断出)

This called a transpose operation. A code sample is here, , but will need significant modification as you have an ArrayList of Arrays (what I infer from your question)

别靠近我心 2024-09-11 03:10:27

也许是这样的

List<List<String>> list = new ArrayList<List<String>>(firstList.size());
for(int i = 0; i < firstList.size(); i++) {
   list.add(Arrays.asList(
      firstList.get(i),
      secondList.get(i),
      thirdList.get(i))
   );
}

something like this maybe

List<List<String>> list = new ArrayList<List<String>>(firstList.size());
for(int i = 0; i < firstList.size(); i++) {
   list.add(Arrays.asList(
      firstList.get(i),
      secondList.get(i),
      thirdList.get(i))
   );
}
仅此而已 2024-09-11 03:10:27

背后的数学原理:您需要转置矩阵。如果使用二维数组或“列表列表”会更容易,这与集合几乎相同。数组列表也可以工作,但它有点令人困惑。

这篇维基百科文章展示了一些转置算法。

The mathematics behind: you need to transpose the matrix. It's easier if you use a 2-dimensional array or a 'List of Lists', which is pretty much he same with collections. A List of arrays works too, but it is slightly more confusing.

This wikipedia article shows some algorithms for transposition.

晒暮凉 2024-09-11 03:10:27

该技术称为转置。实施示例。

public static MyObject [][] transpose(MyObject [][] m){
    int r = m.length;
    int c = m[r].length;
    MyObject [][] t = new MyObject[c][r];
    for(int i = 0; i < r; ++i){
        for(int j = 0; j < c; ++j){
            t[j][i] = m[i][j];
        }
    }
    return t;
}

The technique is called transposing. Example of an implementation.

public static MyObject [][] transpose(MyObject [][] m){
    int r = m.length;
    int c = m[r].length;
    MyObject [][] t = new MyObject[c][r];
    for(int i = 0; i < r; ++i){
        for(int j = 0; j < c; ++j){
            t[j][i] = m[i][j];
        }
    }
    return t;
}
扬花落满肩 2024-09-11 03:10:27

检查所有列表的大小是否相同。

将信息放入矩阵(例如,包含列表元素的列表)中以获取列表的数量和列表的大小。

使用旋转后的尺寸信息创建一个新的矩阵。 (3x4 到 4x3)

实施 2 个 For 循环并将元素放入新矩阵中。

Check whether all lists have the same size.

Place the informations in a Matrix (List with List elements, for example) to get the number of lists and size of a list.

Create a new Matrix with the rotated size informations. (3x4 to 4x3)

Implement 2 For loops and place the elements into the new matrix.

一杯敬自由 2024-09-11 03:10:27

如果是用于数据迁移任务,如果大小不太大,您可以考虑使用友好的电子表格。

对于矩阵操作,jScience 库具有矩阵支持。对于仅仅转置矩阵来说,这有点过分了,但这取决于需要用它做什么。

If it is for a datamigration task, you might consider your friendly spreadsheet if the size is not too big.

For matrix manipulation stuff there is the jScience library which has matrix support. For just transposing a metrix this would be overkill, but it depends what needs to be done with it.

千纸鹤带着心事 2024-09-11 03:10:27

您是否有固定数量的 ArrayList,并且它们一开始就有固定的大小?如果它是固定的,你可以做的是有一个 int 索引值并在同一个循环中依次处理每个 ArrayList。然后,您可以将每个值传输到临时 ArrayList,然后将对此的引用放置在最终 ArrayList 中以进行输出。

听起来很混乱?这是一个粗略的解决方案:

ArrayList tempList = new ArrayList();
ArrayList outputList = new ArrayList();

for(index=0;index<list1.getsize();index++){
// Add null checks and other validation here
tempList.add( list1.get(index) );
tempList.add( list2.get(index) );
tempList.add( list3.get(index) );
outputList.add( tempList );
}

Do you have a fixed number of ArrayLists and are they of fixed size to begin with? If it is fixed, what you can do is have an int index value and process each ArrayList in turn in the same loop. You can then transfer each value to a temporary ArrayList and then place a reference to this in a final ArrayList for output.

Sounds confusing? Here's a rough solution:

ArrayList tempList = new ArrayList();
ArrayList outputList = new ArrayList();

for(index=0;index<list1.getsize();index++){
// Add null checks and other validation here
tempList.add( list1.get(index) );
tempList.add( list2.get(index) );
tempList.add( list3.get(index) );
outputList.add( tempList );
}
说谎友 2024-09-11 03:10:27

由于 get(index) 可能会极大地损害您的性能,即对于大链接列表,我建议使用 @polygenelubricants 解决方案,但使用迭代器方法。

public static <T> List<List<T>> transpose(List<List<T>> table) {
        List<List<T>> ret = new ArrayList<List<T>>();
        final int N = table.stream().mapToInt(l -> l.size()).max().orElse(-1);
        Iterator[] iters = new Iterator[table.size()];

        int i=0;
        for (List<T> col : table) {
            iters[i++] = col.iterator();
        }

        for (i = 0; i < N; i++) {
            List<T> col = new ArrayList<T>(iters.length);
            for (Iterator it : iters) {
                col.add(it.hasNext() ? (T) it.next() : null);
            }
            ret.add(col);
        }
        return ret;
    }

Since get(index) could harm your performance dramatically i.e. for big linked list I would recommend using @polygenelubricants solution but with an iterator approach.

public static <T> List<List<T>> transpose(List<List<T>> table) {
        List<List<T>> ret = new ArrayList<List<T>>();
        final int N = table.stream().mapToInt(l -> l.size()).max().orElse(-1);
        Iterator[] iters = new Iterator[table.size()];

        int i=0;
        for (List<T> col : table) {
            iters[i++] = col.iterator();
        }

        for (i = 0; i < N; i++) {
            List<T> col = new ArrayList<T>(iters.length);
            for (Iterator it : iters) {
                col.add(it.hasNext() ? (T) it.next() : null);
            }
            ret.add(col);
        }
        return ret;
    }
一个人的夜不怕黑 2024-09-11 03:10:27

在 Kotlin 中,简单的转置如下所示:

   fun transpose( matrix: List<List<String>> ) {
        return matrix.first().forEachIndexed { 
            i, _ -> matrix.map { it.getOrNull(i) }
        }
   }

图例:

  • forEachIndexed 迭代第一行的索引。
  • 然后,每个这样的索引都映射到该索引上所有行的项目。 getOrNull 处理较短行中缺失的项目。
  • 它由 map() 作为 List 返回。

In Kotlin, a simple transposing would look like:

   fun transpose( matrix: List<List<String>> ) {
        return matrix.first().forEachIndexed { 
            i, _ -> matrix.map { it.getOrNull(i) }
        }
   }

Legend:

  • forEachIndexed iterates over indexes of the first row.
  • Then, each such index is mapped to the items of all rows on that index. getOrNull handles the missing items in shorter rows.
  • That's returned by map() as a List.
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文