2016-05-03 21 views
5

Bu yüzden okul için çalışıyorum bir program için bir Breadth-First arama fonksiyonu üzerinde çalışıyorum ve belirli bir düğüm için giden kenarlardan geçtiğimde, olası kenarlarımı nasıl geçiyorum?ArrayList <ArrayList <String>> öğesini nasıl sıralayabilirim?

[[A, 1], [D, 1], [C, 2], [D, 2]] 

Ama ne gerçekten istiyorum şudur: bu şuna benzer bir çift ilk endeks düğümün adıdır

[[A, 1], [C, 2], [D, 1], [D, 2]] 

olması ve kenar noktaları ikinci indeks, kenar için etikettir. Aslında bu kenarları alfabetik olarak, önce düğüm adıyla, sonra da etiket ismiyle yapmak istiyorum, ancak bunu nasıl yapacağımı bilmiyorum, çünkü Collections.sort() bir 2B ArrayList için çalışmıyor. Bunu sıralamak için iyi bir yöntem hakkında herhangi bir işaretçi/fikir? Herkese teşekkürler!

DÜZENLEME: Ben 1,8

+0

'[[A, 1], [D, 1] [C, 2], [D, 2]] 'ArrayList >' için geçerli bir örnek değildir. Doğal sıraya göre sıralamak, hatta bir tanımlamak için '.stream(). Sıralanmış()' kullanabilirsiniz. custom "Comparatorser ' –

+0

Bir HashLap'i bir ArrayList ... – RoiEX

+1

RoiEX yerine kullanabilirsiniz, HashMap'i kullanamadı çünkü farklı değerler içeren veya HashMap ... olması gereken bir Anahtar olabilir Bu basit bir şey için oldukça karmaşık bir yapıya dönüşüyor. – jeorfevre

cevap

2

burada tam çalışma kodu Bu atama için JRE 1.7 kullanıyorum. Java SDK8'de lambda ifadesiyle çalışan .

Göreceğiniz gibi basit bir sınıf ve bir karşılaştırıcı ekledim. Bu basit ve güçlüdür.

package com.rizze.test.labs.sof; 

import java.util.ArrayList; 
import java.util.Collections; 
import java.util.Comparator; 
import java.util.List; 

import org.junit.Test; 

public class SOF {  

    public static class Link { 
     public String name; 
     public int id; 

     public static Link build(String n, int i){ 
      Link l = new Link(); 
      l.name = n; 
      l.id=i; 
      return l; 
     } 

     public String toString(){ 
      return String.format("[%s , %d]", name,id); 
     }   
    }  

    @Test 
    public void test() { 

     List<Link> links = new ArrayList<Link>(); 

     //SSETUP [[A, 1], [C, 2], [D, 1], [D, 2]] 
     links.add(Link.build("D", 1)); 
     links.add(Link.build("A", 1)); 
     links.add(Link.build("D", 2)); 
     links.add(Link.build("C", 2)); 


     Collections.sort(links, new Comparator<Link>() {  
      @Override 
      public int compare(Link p1, Link p2) { 
       int ret = p1.name.compareTo(p2.name); 
       if(ret == 0) { 
        ret= p1.id - p2.id; 
       } 
       return ret;    
      }    
     }); 
     System.out.println(links);   
    }  
} 

// Konsol çıkış

Before : [[D , 1], [A , 1], [D , 2], [C , 2]] 
Sorted: [[A , 1], [C , 2], [D , 1], [D , 2]] 

// GİST bağlantı https://gist.github.com/jeorfevre/cbcd7dac5d7fabde6a16db83bdfb7ef5

2

@jeorfevre cevap mükemmel ok. Java sürümünden bahsetmediniz, ancak statik Comparator yöntemleriyle giderim.

çözüm deklaratif olacak ve size kısa ve öz bir şekilde daha fazla kontrol ve netlik verecek:

[[D , 2], [D , 1], [C , 2], [A , 1]] 
:

  Comparator<Edge> comparator = Comparator 
       .comparing(Edge::getName) 
       .thenComparing(Edge::getLabel) 
       .reversed(); 

size verir: Eğer ters sırayla isterseniz

public class Test { 
    public static class Edge { 
     private String name; 
     private int label; 
     public Edge(String name, int id) { 
      this.name = name; 
      this.label = id; 
     } 
     public String toString() { 
      return String.format("[%s , %d]", name, label); 
     } 
     public String getName() { return name; } 
     public int getLabel() { return label; } 
    } 


    public static void main(String[] args) { 
     List<Edge> edges = new ArrayList<>(); 
     edges.add(new Edge("D", 1)); 
     edges.add(new Edge("A", 1)); 
     edges.add(new Edge("D", 2)); 
     edges.add(new Edge("C", 2)); 

     Comparator<Edge> comparator = Comparator 
       .comparing(Edge::getName) 
       .thenComparing(Edge::getLabel); 

     edges.sort(comparator); 

     System.out.println(edges); 
    } 
} 

Ve

  Comparator<Edge> comparator = Comparator 
       .comparing(Edge::getName) 
       .reversed() 
       .thenComparing(Edge::getLabel); 

çıktısı: [[D, 1], [D, 2], [Cı-2], [A, 1]]

+0

Bu harika görünüyor! Tam olarak uygulamakta olduğum şey (Edge sınıfı) ve kenarlarımı nasıl yönetmem gerektiğine dair biraz daha perspektif veriyor. Bir sonraki sorum şu ki, bu kenarlarla bir Edge sınıfında değil, tamamen farklı bir sınıfta çalışıyorum, karşılaştırıcıyı nereye koyayım? Şu an çalışmakta olduğum işlevin içine girer mi?Özür dilerim, Java için nispeten yeni ve karşılaştırıcılar için çok yeni. –

+0

Ayrıca, Edge :: getName ve Edge :: getLabel komutlarıyla ilgili bir sorun yaşıyorum çünkü bu ödev için profesör 1.8 değil JRE 1.7'i kullanmamızı istiyor. Bunu JRE 1.7 kullanarak uygulamak için başka bir yolu var mı? –

İlgili konular