2015-12-07 79 views
1

我有兩個陣列:Java:如何對兩個相應的數組進行排序?

First array: 
25, 20, 50, 30, 12, 11... 

Second Array: 
New York, New Jersey, Detroit, Atlanta, Chicago, Los Angeles 

從所述第二陣列的每個兩個城市對應於從第一個值。

例如:紐約和新澤西州將對應25,底特律和亞特蘭大將對應20等等。

我想按降序對第一個數組的數字進行重新排序(50,30,25,20 ...),但我也希望第二個數組的城市進行相應的移位,以便它們具有相同的值並在排序後。

如何完成此任務? (我可以使用一個ArrayList或Array,取出來的作品簡單)

+1

http://stackoverflow.com/questions/12824423/sort-array-and-reflect-the-changes-in-another-array?lq=1,http://stackoverflow.com/questions/112234/sorting -matched-arrays-in-java?lq = 1(與.NET不同,Java沒有標準庫支持多數組排序) – user2864740

+0

每個數組中的值是否是唯一的? –

+1

你可能更喜歡在java中使用Map來做類似的事情。 http://stackoverflow.com/questions/12824423/sort-array-and-reflect-the-changes-in-another-array?lq=1 http://stackoverflow.com/questions/109383/how-to -sort-A-映射鍵 - 值上的值 - 在-java的 – nullpointer

回答

1

您可以使用TreeMap的:

Map<Integer, String[]> map = new TreeMap<>(); 
for(int i=0;i<firstArray.length;i++){ 
    map.put(firstArray[i], new String[]{secondArray[i * 2], secondArray[i*2+1]}); 
} 

,並且此映射將主要自然順序進行排序。

但我建議你做容器類。喜歡的東西:

public class CityPair{ 
    public int value; 
    public String[] cities = new String[2]; 
} 

現在,你可以通過你的數據填充列表:

... 
ArrayList list = new ArrayList<CityPair>(); 

for(int i=0; i<firstArray.length; i++){ 
    CityPair pair = new CityPair(); 
    pair.value = firstArray[i]; 
    pair.cities[0] = secondArray[i*2]; 
    pair.cities[1] = secondArray[i*2+1]; 
    list.add(pair); 
} 
... 

正如你看到的,我沒有爲檢查索引「索引越界」,但你應該。之後,你可以排序你的列表。你可以做手工使用例如Bubble sort算法,但更好的方法是寫自定義的比較:

public class CityPairComparator implements Comparator<CityPair> { 
    @Override 
    public int compare(CityPair pair1, CityPair pair2) { 
     return Integer.compare(pair1.value, pair2.value); 
    } 
} 

現在你可以用集合實用類的列表進行排序:

Collections.sort(list, new CityPairComparator()); 

有了這個計算策略可以取代String[] citiesCityPair類爲ArrayList<Sting> cities。那麼它將能夠爲每個價值添加兩個以上的城市。

0

這裏的一個(4線)的解決方案,還處理不匹配的數組的長度:

int[] numbers = {25, 20, 50}; 
String[] cities = {"New York", "New Jersey", "Detroit", "Atlanta", "Chicago", "Los Angeles"}; 

Map<Object, Object> map = new TreeMap<>(Comparator.comparing(Integer.class::cast, Integer::compare).reversed()); 
for (Iterator<?> n = Arrays.stream(numbers).iterator(), 
    s = Arrays.stream(String.join(",", cities).split(",(?=(([^,]*,){2})*[^,]*,[^,]*$)")).iterator(); 
    n.hasNext() && s.hasNext();) 
    map.put(n.next(), s.next()); 
numbers = map.keySet().stream().map(String::valueOf).mapToInt(Integer::parseInt).toArray(); 
cities = map.values().stream().map(String::valueOf).map(s -> s.split(",")).flatMap(Arrays::stream).toArray(String[]::new); 

這從每個陣列的數據流創建對飛兩個迭代,都輸入到Object,以允許內部的for循環雙重初始化。城市數組首先被連接成一個字符串,然後被分成兩個字符串(使用適當的正則表達式)。這兩個迭代器的元素都填充了一個TreeMap,它有一個反轉的Integer比較器。

由於TreeMaps迭代中排序順序,keySet()values()一個流可以被用於生成所得到的陣列。

for loop的終端條件檢查兩個迭代器,看看是否有下一個可用元素,如果數組的長度不等,則會導致忽略較長數組的多餘元素。

0

我已經試過這樣一個解決方案,它使用的ArrayList按您的要求:

首先,我已經爲你操作的新的數據結構。由於每個值將舉行兩次城市名稱:

public class Citizen implements Comparable<Citizen> { 

    private int citizenId; 
    private String subjectOne; 
    private String subjectTwo; 


    public Citizen(int rollNumber, String subjectOne, String subjectTwo){ 
     this.citizenId = rollNumber; 
     this.subjectOne = subjectOne; 
     this.subjectTwo = subjectTwo; 
    } 

    public int getRollNumber() { 
     return citizenId; 
    } 
    public void setRollNumber(int rollNumber) { 
     this.citizenId = rollNumber; 
    } 
    public String getSubjectOne() { 
     return subjectOne; 
    } 
    public void setSubjectOne(String subjectOne) { 
     this.subjectOne = subjectOne; 
    } 
    public String getSubjectTwo() { 
     return subjectTwo; 
    } 
    public void setSubjectTwo(String subjectTwo) { 
     this.subjectTwo = subjectTwo; 
    } 


     public int compareTo(Citizen comparestu) { 
      int compareage=((Citizen)comparestu).getRollNumber(); 
      /* For Ascending order*/ 
      return this.citizenId-compareage; 

      /* For Descending order do like this */ 
      //return compareage-this.studentage; 
     } 

     @Override 
     public String toString() { 
      return "[ rollno=" + citizenId + ", subjectOne=" + subjectOne + ", subjectTwo=" + subjectTwo + "]"; 
     } 
} 

正如你可以在這裏看到比較的參數是使用實現可比接口作爲citizenID。

現在就撥打:

public static void main(String[] args) { 

     ArrayList<Citizen> studentList = new ArrayList<Citizen>(); 

     studentList.add(new Citizen(25, "New York", "New Jersey")); 
     studentList.add(new Citizen(20, "Detroit", "Atlanta")); 
     studentList.add(new Citizen(50, "Chicago", "Los Angeles")); 
     studentList.add(new Citizen(30, "Kolkata", "Delhi")); 
     studentList.add(new Citizen(12, "Munmbai", "Baranasi")); 
     studentList.add(new Citizen(11, "Bangalore", "Goa")); 



     Collections.sort(studentList); 
      for(Citizen student: studentList){ 
       System.out.println(student); 
      } 
    } 

輸出:

[ rollno=11, subjectOne=Bangalore, subjectTwo=Goa] 
[ rollno=12, subjectOne=Munmbai, subjectTwo=Baranasi] 
[ rollno=20, subjectOne=Detroit, subjectTwo=Atlanta] 
[ rollno=25, subjectOne=New York, subjectTwo=New Jersey] 
[ rollno=30, subjectOne=Kolkata, subjectTwo=Delhi] 
[ rollno=50, subjectOne=Chicago, subjectTwo=Los Angeles] 
0

的Java 8提供了一個稍微更優雅的方式來做到這一點,而無需單獨的地圖:

int[] array1; 
String[] array2; 

array2 = IntStream.range(0, Math.min(array1, array2)) 
    .boxed().sorted(Comparator.comparingInt(i -> array1[i])) 
    .map(i -> array2[i]) 
    .toArray(array2); 

拳擊僅需要,因爲IntStream沒有使用自定義的sorted方法Comparator。我不確定爲什麼不。

如果您想以List結尾,請使用.collect(Collectors.toList())而不是toArray

相關問題