【问题标题】:How do I reorder another array based on a sorted array Java? [closed]如何基于已排序数组 Java 重新排序另一个数组? [关闭]
【发布时间】:2021-07-10 20:25:55
【问题描述】:

给定一个未排序的数组可能包含重复的元素

int [] nums = {8,1,2,2,3};
Arrays.sort(nums);

另一个数组

int[] count = {0,1,1,3,4};

我想实现这样的目标

Arrays.reorder(count, k->nums.sort());
int[] count = {4,0,1,1,3};

同时考虑 Count 数组是从 nums 数组按排序顺序计算得到的。

【问题讨论】:

  • 澄清一下,你是说给定一些数组 A 和另一个 B,你希望 B 匹配与 A 相同的排名顺序吗? IE。如果 A 中的最大数字在索引 x 处,则 B 中的最大数字应该在索引 x 处,依此类推,从第二高一直到最低。
  • 没有更多信息,可能有多种解决方案。在某些情况下,如果nums 数组具有重复值而count 数组没有重复值,则可能无法确定将哪个重复索引应用于count 数组值。因此,您需要详细说明(而不是举例)适用的规则。
  • 您的编辑没有说明您想要做什么。您需要用文字指定。假设nums = {8,2,1,2,3}count = {0,1,2,3,4} Imo,有两个可能的答案,4,1,0,2,34,2,0,1,3。那么它是哪一个,为什么?如果我错了,那又是为什么?

标签: java arrays sorting


【解决方案1】:

如果我们对索引数组而不是原始数组进行排序,我们会得到元素的顺序:

Integer[] nums = {8,1,2,2,3};

Integer[] order = new Integer[nums.length];
Arrays.setAll(order, i->i);
Arrays.sort(order, (a, b) -> nums[a] - nums[b]);

System.out.println(Arrays.toString(order));

给予:

[1, 2, 3, 4, 0]

这表示第二个数组中所需的值排列。

我们现在可以使用standard algorithm 来按照指定的顺序排列一个数组:

static <T> void reorder(T[] a, Integer[] order)
{
    for(int i=0; i<a.length; i++)
    {
        while(order[i] != i) 
        {
            swap(a,     order[i], i);
            swap(order, order[i], i);
        }           
    }
}

static <T> void swap(T[] a, int i, int j)
{
    T tmp = a[i];
    a[i] = a[j];
    a[j] = tmp;
}

把这些放在一起

Integer[] nums = {8,1,2,2,3};

Integer[] order = new Integer[nums.length];
Arrays.setAll(order, i->i);
Arrays.sort(order, (a, b) -> nums[a] - nums[b]);

Integer[] count = {0,1,1,3,4};
reorder(count, order);

System.out.println(Arrays.toString(count));

输出:

[4, 0, 1, 1, 3]

【讨论】:

    【解决方案2】:

    从您的示例中,您似乎想要匹配两个数组之间的排名顺序。如果我在这里错了,请告诉我,但要进一步分解您的示例:

    // Ranking order here is [4, 0, 1, 2, 3]
    int[] first = {8,1,2,2,3};
    
    int[] second = {0,1,1,3,4};
    // If we apply the same ranking order to second we get the following
    // {4, 0, 1, 1, 3}
    

    假设这是您想要的,类似以下的内容会起作用。我不知道这样做的简单库方法。

    import java.util.HashMap;
    import java.util.List;
    import java.util.stream.Collectors;
    
    public final class RankOrdering {
    
        public static List<Integer> applyRankOrdering(List<Integer> source, List<Integer> target) {
            if (source.size() != target.size()) {
                throw new IllegalArgumentException("source and target must be the same size");
            }
    
            // Generate the ranking order for the source list: [3, 5, 1, 0, 0] -> [3, 4, 2, 1, 0]
            var sourceSorted = source.stream().sorted().collect(Collectors.toList());
            var sourceValuesToRank = new HashMap<Integer, Integer>();
            for (int i = 0; i < sourceSorted.size(); i++) {
                sourceValuesToRank.put(sourceSorted.get(i), i);
            }
            var sourceRankOrder = source
                    .stream()
                    .map(sourceValuesToRank::get)
                    .collect(Collectors.toList());
    
            // Determine which rank each element of target has
            var targetSorted = target.stream().sorted().collect(Collectors.toList());
            var targetRankToValue = new HashMap<Integer, Integer>();
            for (int i = 0; i < targetSorted.size(); i++) {
                targetRankToValue.put(i, targetSorted.get(i));
            }
    
            // Apply source ranking order to the values from target
            return sourceRankOrder
                    .stream()
                    .map(targetRankToValue::get)
                    .collect(Collectors.toList());
        }
    
        public static void main(String[] args) {
            var source = List.of(8, 1, 2, 2, 3);
            var target = List.of(0, 1, 1, 3, 4);
            System.out.println(applyRankOrdering(source, target));
        }
    }
    

    哪些打印:

    [4, 0, 1, 1, 3]
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-10-25
      • 1970-01-01
      • 2021-07-17
      • 2019-04-25
      • 1970-01-01
      • 1970-01-01
      • 2017-06-24
      相关资源
      最近更新 更多