Me ajudem array de file como ordenar?

12 respostas
M

tenho um array de file mais nao consigo ordenar. ele ordena errado

rev_1
rev_10
rev_11
rev_2

sendo que devia ser

rev_1
rev_2
rev_10
rev_11

estou usando

Arrays.sort(arrayRevistas = new File(caminhoR).listFiles(), NameFileComparator.NAME_SYSTEM_COMPARATOR);

e

Arrays.sort(arrayRevistas = new File(caminhoR).listFiles());

12 Respostas

M

usei tambem

NameFileComparator.NAME_INSENSITIVE_COMPARATOR

e acontece a meisma coisa

E

NameFileComparator.NAME_INSENSITIVE_COMPARATOR
- Ou seja, programação via tentativa e erro - você leu a documentação?

Por que é que essa ordem está errada? Ela é a ordem lexicográfica normal. Não há nenhum desses “file comparators” prontos que ordene do jeito que vocë quer.

(Primeira vez que vejo a palavra “meisma”. Dona Maria, tu és carioca? Só para saber.

Acontece que o Windows Explorer, para facilitar, ordena os arquivos de forma que, se houver um prefixo numérico ou um sufixo numérico, quebra o nome do arquivo em pedaços e leva isso em conta.

Se vocë tiver um pouco de paciência, pode escrever um comparador que faça exatamente o que você quer. Para simplificar, vou escrever um exemplo de comparador que verifica se 2 strings têm um prefixo numérico (não vou resolver o caso do sufixo, mas se você for esperta suficiente, vai entender).

O que estou dizendo é que o comparador que vou apresentar abaixo seria algo que deixaria, por exemplo, a seguinte listagem em ordem:

1cervejas
5cervejas
10cervejas
150cervejas

E
package guj;

import java.io.File;
import java.util.Arrays;
import java.util.Comparator;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class NumericFileNameComparator implements Comparator<File> {

    private static Pattern patPrefixoNumerico = Pattern.compile ("([0-9]+)(.*)");
    private static int compareFilenames (String filename1, String filename2) {
        // Comparamos a parte numerica e a parte nao-numerica em separado
        Matcher matcher1 = patPrefixoNumerico.matcher(filename1);
        Matcher matcher2 = patPrefixoNumerico.matcher(filename2);
        if (matcher1.matches() && matcher2.matches()) {
            int ret = Long.valueOf(matcher1.group(1)).compareTo(Long.valueOf(matcher2.group(1)));
            if (ret != 0)
                return ret;
            else return matcher1.group(2).compareToIgnoreCase(matcher2.group(2));
        }
        // Se nao tiver prefixo numerico...
        return filename1.compareToIgnoreCase(filename2);
    }
    
    @Override
    public int compare(File f1, File f2) {
        if ((f1.getParent() != null && f2.getParent() != null && f1.getParent().equalsIgnoreCase(f2.getParent()))
                || (f1.getParent() == null && f2.getParent() == null))
            return compareFilenames (f1.getName(), f2.getName());
        else
            return f1.compareTo(f2);
    }

    /**
     * Teste simples 
     */
    public static void main (String[] args) {
        File[] nomes = new File[]{
            new File ("500cervejas"),
            new File ("10cervejas"),
            new File ("15biritas"),
            new File ("2cervejas"),
            new File ("15cervejas")
        };
        Arrays.sort (nomes, new NumericFileNameComparator());
        // Deve imprimir:
        // 2cervejas
        // 10cervejas
        // 15biritas
        // 15cervejas
        // 500cervejas

        for (File f : nomes) {
            System.out.println (f);
        }
    }
}

Bom dia internacional da cerveja - fui!

M

oi. sou carioca sim parece? como soube? rss

obrigada. mais nao entendi seu codigo achei muito avancado

pode continuar me ajudando?? ?

M

nossa e dificil meismo esse codigo uso e java avançado ne?? ?

regis_hideki

Os nomes dos arquivos seguem o padrão “rev_algumNumero” ou não necessariamente?

Se o padrão for seguido, basta usar o método substring da classe String para pegar o “algumNumero”, tranformá-lo em número com o método valueOf da classe Integer e ordená-los.

M

regis_hideki:
Os nomes dos arquivos seguem o padrão “rev_algumNumero” ou não necessariamente?

Se o padrão for seguido, basta usar o método substring da classe String para pegar o “algumNumero”, tranformá-lo em número com o método valueOf da classe Integer e ordená-los.

oi. infelizmente nao, o nome pode ser qualquer um meu chefe disse, e nem sempre tambem ira terminar com _algumnumero.

A

mariazinhahappy:
regis_hideki:
Os nomes dos arquivos seguem o padrão “rev_algumNumero” ou não necessariamente?

Se o padrão for seguido, basta usar o método substring da classe String para pegar o “algumNumero”, tranformá-lo em número com o método valueOf da classe Integer e ordená-los.

oi. infelizmente nao, o nome pode ser qualquer um meu chefe disse, e nem sempre tambem ira terminar com _algumnumero.

Antes d td é preciso entender bem claramente o padrão a ser embasado, tentei inferir através de seus posts e conclui q vc
esteja tentando partir do seguinte:

// O primeiro bloco antes do underline pode ser qlq. coisa (texto, número ou até mesmo underline)
// O último é sempre número, se houver
??????????_??????????????????

Por favor, confirme se é isto mesmo.
B

Vamos tentar ver esse problema por outro lado:

Você tem controle sobre como os nomes dos arquivos são gerados? Se tiver, seria mais fácil colocar o nome como rev_0000001, rev_0000002, e assim vai.

M

andredecotia:
mariazinhahappy:
regis_hideki:
Os nomes dos arquivos seguem o padrão “rev_algumNumero” ou não necessariamente?

Se o padrão for seguido, basta usar o método substring da classe String para pegar o “algumNumero”, tranformá-lo em número com o método valueOf da classe Integer e ordená-los.

oi. infelizmente nao, o nome pode ser qualquer um meu chefe disse, e nem sempre tambem ira terminar com _algumnumero.

Antes d td é preciso entender bem claramente o padrão a ser embasado, tentei inferir através de seus posts e conclui q vc
esteja tentando partir do seguinte:

// O primeiro bloco antes do underline pode ser qlq. coisa (texto, número ou até mesmo underline)
// O último é sempre número, se houver
??????????_??????????????????

Por favor, confirme se é isto mesmo.

e isssso

M

Bruno Laturner:
Vamos tentar ver esse problema por outro lado:

Você tem controle sobre como os nomes dos arquivos são gerados? Se tiver, seria mais fácil colocar o nome como rev_0000001, rev_0000002, e assim vai.

oi. mais como e possivel eu tentei fazer mais naum aparece o zero

Long valorComOResultadoFinalDepoisDeTerminadoEIgualA = 000000000;

valorComOResultadoFinalDepoisDeTerminadoEIgualA = valorComOResultadoFinalDepoisDeTerminadoEIgualA + 3;

regis_hideki

mariazinhahappy:
Bruno Laturner:
Vamos tentar ver esse problema por outro lado:

Você tem controle sobre como os nomes dos arquivos são gerados? Se tiver, seria mais fácil colocar o nome como rev_0000001, rev_0000002, e assim vai.

oi. mais como e possivel eu tentei fazer mais naum aparece o zero

Long valorComOResultadoFinalDepoisDeTerminadoEIgualA = 000000000;

valorComOResultadoFinalDepoisDeTerminadoEIgualA = valorComOResultadoFinalDepoisDeTerminadoEIgualA + 3;

O problema de usar Long nesse caso, é que 0000 == 0, e o número é colocado na sua forma mais enxuta.

Nesse caso, é preciso trabalhar com String.

Uma maneira mais imediata para quem está começando, é pegar o número (no seu caso, o 3), tranformá-lo em String e inserir zeros à esquerda até que o tamanho da String fique do tamanho que você quer.

A maneira mais simples é usar uma classe chamada NumberFormat:
http://www.google.com.br/webhp?sourceid=chrome-instant&ion=1&ie=UTF-8#hl=pt-BR&tbo=d&sclient=psy-ab&q=numberformat+java+zeros+a+esquerda&oq=numberformat+java+zeros+a+esquerda&gs_l=hp.12...0.0.2.5416.0.0.0.0.0.0.0.0..0.0...0.0...1c..3.psy-ab.CvKTcgLLaRo&pbx=1&bav=on.2,or.r_gc.r_pw.r_qf.&bvm=bv.42553238,d.eWU&fp=d15c5797536c9822&ion=1&biw=1846&bih=995

Criado 15 de fevereiro de 2013
Ultima resposta 17 de fev. de 2013
Respostas 12
Participantes 5