Oito algoritmos de classificação - classificação de bolhas (compreensão de imagens em movimento)

Tipo de bolha

idéias de algoritmo

O princípio da classificação de bolhas é: da esquerda para a direita, os elementos adjacentes são comparados. Cada rodada de comparação, seja a maior ou a menor na sequência, é encontrada. Este número emergirá da extrema direita da sequência.

Tomando a classificação de pequeno para grande como exemplo, após a primeira rodada de comparação, o maior número entre todos os números flutuará para a extrema direita; após a segunda rodada de comparação, o segundo maior número entre todos os números flutuará até o penúltimo posições... basta comparar rodada após rodada e, finalmente, obter a classificação de pequeno para grande.
 

animação

 

código do algoritmo

 public static void bubbleSort(int[] a){
    for (int i = 0; i < a.length-1; i++) {//a.length-1是因为不用与自己比较,所以比的数就少一个
         for (int j = 0; j < a.length-1-i; j++){//a.lenght-1-i是因为每一趟就会少一个数比较
             if(a[j]>a[j+1]){
                  int tmp = a[j];
                  a[j] = a[j+1];
                  a[j+1]  = tmp;
             }
         }
     }
  }

O código acima ainda possui algumas deficiências, caso uma sequência já esteja ordenada, ou já esteja ordenada no meio da ordenação. Mas o tipo de bolha ainda passará por dois loops for e a complexidade de tempo é sempre O(n^2) . Por isso, podemos melhorar o código, adicionar um flag antes de cada comparação , se o número for trocado, alterar o flag, indicando que a sequência não está em ordem. Se o sinalizador não mudar após uma comparação, significa que a sequência já está em ordem e não há necessidade de repetir o loop. Neste momento, a complexidade de tempo pode ser melhor alterada para O(n) .

Otimizado

 public static void bubbleSort(int[] a){

        for (int i = 0; i < a.length-1; i++) {
            int flag = 0;  //添加标记
            for (int j = 0; j < a.length-1-i; j++) {
                if(a[j]>a[j+1]){
                    int tmp = a[j];
                    a[j] = a[j+1];
                    a[j+1]  = tmp;
                    falg++;
                }
            }
            if(flag==0) break; //即falg在经过for循环后,还为0 说明已排好序了,就不用再进行排序
        }                      
    }

Análise de Complexidade

Complexidade de tempo  O(n^2) Após a otimização, o melhor caso se torna o(n)

teste de complexidade de tempo

Em seguida, vamos tentar testá-lo com muitos dados.

int[] a = new int[10_0000]; //teste de 100.000 dados

1. A função orderArray é implementada para gerar uma sequência ordenada básica, ou seja, organizada do menor para o maior.

public static void orderArray(int[] a) {
        for (int i = 0; i < a.length; i++) {
            a[i] = i;
        }
 }

2. A função notOrderArray gera uma sequência inversa, ou seja, organizada do maior para o menor.

public static void notOrderArray(int[] a) {
        for (int i = 0; i < a.length; i++) {
            a[i] = a.length-i;
        }
}

3. A função randomArray gera um array aleatório não ordenado.

 public static void randomArray(int[] a) {
        Random random = new Random();
        for (int i = 0; i < a.length; i++) {
            a[i] = random.nextInt(10_0000);
        }
 }

4. A função testInsertSort testa o valor de retorno de System.currentTimeMillis() em milissegundos.

 public static void testInsertSort(int[] a){
        int[] tmpArray = Arrays.copyOf(a,a.length);
        long startTime = System.currentTimeMillis();    //注意用long接收
        shellSort(tmpArray);
        long endTime = System.currentTimeMillis();  //返回单位是毫秒
        System.out.println("冒泡排序耗时:"+(endTime-startTime));
 }

5. Execução da chamada da função principal

public static void main(String[] args) {
 
 
        int[] a = new int[10_0000];
        //有序
        System.out.println("基本有序数列");
        orderArray(a);
        testInsertSort(a);
 
        //倒序
        System.out.println("逆序数列");
        notOrderArray(a);
        testInsertSort(a);
 
        //随机乱序
        System.out.println("无序数列");
        randomArray(a);
        testInsertSort(a);
 
}

resultado da operação

    

 Por comparação, verifica-se que a complexidade de tempo após a melhoria ainda é reduzida.

código completo

import java.util.Random;

public class sort {

    public static void main(String[] args) {
    
        int[] a = new int[10_0000];
        
        //有序
        System.out.println("基本有序数列");
        orderArray(a);
        testInsertSort(a);

        //无序
        System.out.println("逆序数列");
        notOrderArray(a);
        testInsertSort(a);

        //乱序
        System.out.println("无序数列");
        randomArray(a);
        testInsertSort(a);

    }


    //冒泡排序
    //时间复杂度 O(n^2)   优化后 最好情况 O(n)
    public static void bubbleSort(int[] a){
        for (int i = 0; i < a.length; i++) {
            for (int j = 0; j < a.length-1-i; j++) {
                if(a[j]>a[j+1]){
                    int tmp = a[j];
                    a[j] = a[j+1];
                    a[j+1]  = tmp;
                }
            }
        }
    }


    //优化后的冒泡排序
    public static void bubbleSort1(int[] a){

        for (int i = 0; i < a.length; i++) {
            int flag = 0;
            for (int j = 0; j < a.length-1-i; j++) {
                if(a[j]>a[j+1]){
                    int tmp = a[j];
                    a[j] = a[j+1];
                    a[j+1]  = tmp;
                    flag++;
                }
            }
            if(flag==0) break;
        }
    }


    //生成有序数组  从小到大排列
    public static void orderArray(int[] a) {
        for (int i = 0; i < a.length; i++) {
            a[i] = i;
        }
    }


    //n无序 其实就是从大到小排列
    public static void notOrderArray(int[] a) {
        for (int i = 0; i < a.length; i++) {
            a[i] = a.length-i;
        }
    }

    //乱序 随机生成序列
    public static void randomArray(int[] a) {
        Random random = new Random();
        for (int i = 0; i < a.length; i++) {
            a[i] = random.nextInt(10_0000);
        }
    }

    //大量数据测试
    public static void testInsertSort(int[] a){
        int[] tmpArray = Arrays.copyOf(a,a.length);
        long startTime = System.currentTimeMillis();    //注意用long接收
        bubbleSort1(tmpArray);
        long endTime = System.currentTimeMillis();
        System.out.println("改进冒泡排序耗时:"+(endTime-startTime));
    }

}

Não é fácil de criar, se este blog for útil para você, lembre-se de deixar uma mensagem + curtir.

Acho que você gosta

Origin blog.csdn.net/m0_73381672/article/details/132028979
Recomendado
Clasificación