Ordenar list com vários atributos

Boa tarde,

Preciso de uma ajuda…

Tenho uma lista de objetos pessoa. Em cada objeto da lista tem o nome, idade, rg, cidade, profissao, data de nascimento…

Quero ordenar esta lista conforme o usuário escolhe:
Ele pode querer ordenar por cidade e profissao ou somente por nome. O atributo de ordenação é dinâmico e a cada consulta ele pode escolher a ordenção por um atributo ou vários.
Isso é possível? Alguém tem idéia? Achei mt coisa na net, mas é somente um atributo fixo.

Obrigado!

Pesquise por Collections.sort http://download.oracle.com/docs/cd/E17409_01/javase/6/docs/api/java/util/Collections.html e a interface Comparator http://download.oracle.com/docs/cd/E17476_01/javase/1.5.0/docs/api/java/util/Comparator.html .

Abraços.

Acho que da pra fazer com um Comparator personalizado.
Por exemplo:

class MeuComparador implements Comparator<MinhaClasse> {
			public static final int POR_NOME = 1;
			public static final int POR_DESC = 2;
			int tipoComparacao;
			
			public MeuComparador(int tipoComparacao) {
				this.tipoComparacao = tipoComparacao;
			}
			
			@Override
			public int compare(MinhaClasse objeto1, MinhaClasse objeto2) {
				int retorno = 0;
				
				switch (this.tipoComparacao) {
					case POR_NOME:
						retorno = objeto1.getNome().compareTo(objeto2.getNome());
						break;
					case POR_DESC:
						retorno = objeto1.getDesc().compareTo(objeto2.getDesc());
						break;
					default:
						throw new RuntimeException("opcao invalida");
				}
				return retorno;
			}
		}; 

Daí então voce pode utilizar da seguinte forma:

List<MinhaClasse> list = new ArrayList<MinhaClasse>();
		
list.add(new MinhaClasse("ze", "padeiro"));
list.add(new MinhaClasse("bruno", "analista"));
list.add(new MinhaClasse("carla", "dentista"));
// ordernar por nome
Collections.sort(list, new MeuComparador(MeuComparador.POR_NOME));
// ou por descricao/profissao
Collections.sort(list, new MeuComparador(MeuComparador.POR_DESC));

abração

[quote=luizsodrerj]Acho que da pra fazer com um Comparator personalizado.
Daí então voce pode utilizar da seguinte forma:

List<MinhaClasse> list = new ArrayList<MinhaClasse>();
		
list.add(new MinhaClasse("ze", "padeiro"));
list.add(new MinhaClasse("bruno", "analista"));
list.add(new MinhaClasse("carla", "dentista"));
// ordernar por nome
Collections.sort(list, new MeuComparador(MeuComparador.POR_NOME));
// ou por descricao/profissao
Collections.sort(list, new MeuComparador(MeuComparador.POR_DESC));

[/quote]

Exato. na hora do sorte, vc busca no request oq foi que o cliente escolheu.

Eu sei também que existem bibliotecas que fornecem grids que vc pode ordenar sem precisar mandar outro request. Pena que esqueci o nome, lembro que ele coloca as setas na coluna e depois ordena apenas por clicar.

Manda um google nisso ae que tu acha. [=

Como o java não tem nada tão legal quando o LINQ do .Net, você será obrigado a criar um comparator para cada atributo que você quiser ordenar. Esse link explica em detalhes a teoria disso:
http://www.guj.com.br/posts/list/45985.java#241201

Se você quiser ordenar esse list para exibir num JTable, dê uma olhada no auto-filtro, no meu link.

Bom dia,

Pelo que pesquisei só existe uma ordenação por vez (nome ou codigo).
Terei que ordernar primeiro por nome e depois comparar todos os nomes que são iguais (comparator) e ir ordenando a descrição e ir jogando na lista.
É isso?
Obrigado

Para ordenar por dois atributos ao mesmo tempo, basta escrever um Comparator para isso:

[code]public class ComparadorPorCidadeEProfissao extends Comparator<MinhaClasse>
{
public int compare(MinhaClasse o1, MinhaClasse o2) {
int cidade = o1.getCidade().compare(o2.getCidade());
if (cidade != 0) return cidade; //Caso as cidades sejam diferentes, ordena pela cidade.

   //Se forem iguais, vamos ordenar pela profissão.
   int prof = o1.getProfissao().compare(o2.getProfissao());
   if (prof != 0) return prof; 

   //Se as profissões forem iguais, ordenamos pelo nome
   return o1.getNome().compareTo(o2.getNome());

}[/code]

Uma lista contendo:
Curitiba, Engenheiro Civil, Marcio
Curitiba, Analista de Sistemas, Vinicius
Anápolis, Zootecnico, Pedro
Curitiba, Veterinário, Marcelo
Curitiba, Engenheiro Civil, Andreia
Anápolis, Botânico, Laura

Ficaria ordenada usando aquele comparador assim:
Anápolis, Botânico, Laura
Anápolis, Zootecnico, Pedro
Curitiba, Analista de Sistemas, Vinicius
Curitiba, Engenheiro Civil, Andreia
Curitiba, Engenheiro Civil, Marcio
Curitiba, Veterinário, Marcelo

Como você quer filtros dinâmicos, ainda recomendo o uso de um JTable no lugar de um JList, e da classe de auto-filtro, do link abaixo. Ela não só faz ordenação como filtragem também, igualzinho ao MS Excel. Usuários tendem a gostar muito dela. :slight_smile:

Boa tarde,

Vou receber uma lista contendo a ordem que terei que ordenar meu list.
Como não sei quantos parametros o usuário vai querer ordenar fiz um Case.
Se o tamanho da lista for 2, vou entrar no case 2 e Ordenar primeiro por cidade e depois por nome.

class Ordem {   
    String nome;   
    String cidade;   
    String prof;   
    public Ordem(String c, String p, String n) {   
       nome = n; cidade = c; prof = p;   
    }   
    public String toString() {   
        return cidade + " - " + prof + "  - " + nome;   
    }   
    public String getcidade() {
        return cidade;
      }
    public String getprof() {
        return prof;
      }
      
    public String getnome() {
          return nome;
        }
}   
	          
class Personarator implements  Comparator<Ordem>  
         {  
	int qtparametros = 3;
	public int compare(Ordem emp1, Ordem emp2) { 
	          		  int retorno = 0;  
	          		  
	          		  switch (this.qtparametros) {  
	                     case 1:  
	                        retorno = emp1.getnome().compareTo(emp2.getnome());  
	                         break;  
	                     case 2:  
	                    	 retorno = emp1.getcidade().compareTo(emp2.getcidade()); 
	                    	 if (retorno != 0) return retorno;
	                    	 retorno = emp1.getnome().compareTo(emp2.getnome());  
	                    	 break;
	                     case 3:  
	                    	 retorno = emp1.getcidade().compareTo(emp2.getcidade()); 
	                    	 if (retorno != 0) return retorno;
	                    	 retorno = emp1.getprof().compareTo(emp2.getprof());  
	                    	 if (retorno != 0) return retorno;
	                    	 retorno = emp1.getnome().compareTo(emp2.getnome());  
	                          break;  
	                      default:  
	                         throw new RuntimeException("opcao invalida");  
	                   }  
	                return retorno;  
	                } 
	           }

Como eu não sei a sequência que o usuário vai querer ordernar, o parametro1 seria a primeira escolha (nome ou cidade) e o segundo a segunda escolha assim sucessivamente…
Isso é possível?

      case 2:  
	 retorno = emp1.getParametro1().compareTo(emp2.getParametro1()); 
	  if (retorno != 0) return retorno;
	 retorno = emp1.getParametro2e().compareTo(emp2.getParametro2());  
      break;

Obrigado