Java 从已排序数组的数组中获取N个已排序项

Java 从已排序数组的数组中获取N个已排序项,java,android,sorting,multidimensional-array,arraylist,Java,Android,Sorting,Multidimensional Array,Arraylist,我有一个多维的日期数组,严格来说是一个ArrayList。我需要生成一个新的一维ArrayList,它由前面提到的多维数组的所有数组中的项组成 我的第一个想法是将所有的ArrayList连接在一起并对它们进行排序,但是由于我不知道每个级别中的元素数量,并且只需要生成的数组中一定数量的元素,这将有点太多内存和处理器负担重。 我的意思是,如果我将所有的Date元素加入一个ArrayList,我可能会得到一个包含数千个日期的ArrayList。。。最终将其修剪到前20个。这就是我放弃这个解决方案的原因

我有一个多维的日期数组,严格来说是一个
ArrayList
。我需要生成一个新的一维
ArrayList
,它由前面提到的多维数组的所有数组中的项组成

我的第一个想法是将所有的ArrayList连接在一起并对它们进行排序,但是由于我不知道每个级别中的元素数量,并且只需要生成的数组中一定数量的元素,这将有点太多内存和处理器负担重。 我的意思是,如果我将所有的
Date
元素加入一个
ArrayList
,我可能会得到一个包含数千个日期的ArrayList。。。最终将其修剪到前20个。这就是我放弃这个解决方案的原因

那么,我可以使用哪种算法将N(或2)个级别的元素排序为1

编辑

ArrayList<Date> a1 = new ArrayList<Date>();
a1.add(new Date(15));
a1.add(new Date(16));
a1.add(new Date(23));

ArrayList<Date> a2 = new ArrayList<Date>();
a2.add(new Date(1));
a2.add(new Date(25));
a2.add(new Date(89));

ArrayList<Date> a3 = new ArrayList<Date>();
a3.add(new Date(64));
a3.add(new Date(72));
a3.add(new Date(73));

ArrayList<ArrayList<Date>> b = new ArrayList<ArrayList<Date>>();
b.add(a1);
b.add(a2);
b.add(a3);

在本例中,只有3个
ArrayList
,但在实践中,我不知道数字,因此我认为移动设备的最佳解决方案不是加入所有二级ArrayList并对新的大ArrayList进行排序,前提是只使用多个项目。

根据您对问题的描述,我能想到的一些解决方案是:

  • 当然是您建议的,即附加所有数组,然后对它们进行排序,并获取前20个数组
  • 分别对每个内部数组进行排序,然后根据合并排序算法执行类似于合并的过程,以合并所有这些内部数组中的前20个项目,并在合并所需数量的项目(例如20个项目)时中断合并循环
  • 对每个内部数组进行排序,同时将日期放入其中。这样你就不必重复每一个后记了。然后像上面所说的那样进行合并
  • 如果在多个内部数组中有多个项,并且您想要其中的前20个项,那么您必须迭代内部数组以某种方式进行排序。这是我能想到的3个解决方案,欢迎任何人加入我的帖子

    编辑:

    四,。 我能想到的另一种方法是:通过扫描整个内部数组数组来构建优先级队列(最小堆)。这将是一个深度有限的树,即,由于您需要20个元素,树的最大深度可以是4(假设根为0)。堆中允许的最大项目数为20。这种方法将在O(logn)时间内为您提供解决方案。当然,您将花费O(N)个时间扫描整个列表中的每个项目,并且构建该堆可能会占用额外的空间。

    我将提出一个解决方案。这可能相当复杂,但会使您的运行时间与元素总数成线性关系

    我将进行以下工作:

  • 每个列表有一个锦标赛并存储锦标赛树(这棵树可能很简单:每个元素,保留一个对手列表和结果)
  • 在获胜者之间举办一场比赛,并存储比赛树
  • 第一个要素是锦标赛2的获胜者
  • 第二个要素是在锦标赛1或锦标赛2中胜利者的输家
  • 第三个要素是在锦标赛1或锦标赛2中nr2的输家
  • 等等

  • 我需要生成…
    。只有你试一下,它才会发生。你能更具体一点吗?听起来你(至少在心理上)解决了这个问题,并说这不是你想要的。在字里行间,我读到你想要前20次约会,而不是把整个名单排序。这是一个不同的问题,比排序有更快的解决方案。请明确你想要什么。@KarthikT我最初对解决方案的想法非常耗费资源。如果我加入所有的
    Date
    元素,我可以处理大量的日期,实际上我只需要使用其中的一部分。这就是为什么我认为我需要一个更优化的解决方案。@Jago困惑是因为你的问题恰恰是这样问的。。所以我希望你遗漏了一些细节,或者这个问题可以用更好的措辞。听起来是个不错的解决方案。我只是想知道,在移动设备中,它是否比将所有元素合并到一个arraylist中并对其进行排序更消耗资源…?@Jago这是个好问题。存储将是
    O(n)
    ,但我不太确定该常数。在使用坏常数的线性算法优于使用好常数的
    nlogn
    算法(例如默认的快速排序)之前,需要一个巨大的数组。不过,当你遇到性能问题时,你可以考虑这种方法,因为你有很多的日期。我认为这种方法消耗了太多的空间,并且考虑到它在手机上做的几乎是不可行的。不是一大堆的日期,也不是一场比赛。。。似乎是合理的…是的,但如果有许多包含许多元素的内部数组,这种方法可能会做得更糟。唯一的优势是合并排序的最坏情况仍然是O(N logn),所以这仍然是一个胜利。因此,明智地选择。如果你正在考虑2),想要一个编程费用相当低的解决方案,并且对O(n*logn)的复杂性感到满意,那么尝试将所有日期收集到一个树形图中,它会自动对它们进行排序。然后可以调用myTreeMap.firstKey()n次。如果要删除重复项,请改用树集。
    getLatestDates(b, 5) = {Date (89), Date(73), Date(72), Date(64), Date(25)};