9
votes

Comprendre la récursion (appliquer sur le tri de la bulle)

J'essaie de déterminer comment utiliser la récursion dans les programmes. Je comprends comment la récursivité fonctionne dans des exemples classiques comme "factorielles", mais je ne suis pas sûr de savoir comment l'appliquer seul ...

Je commence à convertir un code de tri de bulle itératif en un code récursif ... J'ai cherché sur le net pour la même chose ... mais je ne suis pas capable de trouver une solution / explication convaincante.

Exemple de code itératif pour la tri de la bulle est:

arr [ n] -> Array avec des éléments (1..n) qui doit être trié xxx

se sentirait utile si quelqu'un pouvait donner un indice sur la façon de se faire ...


3 commentaires

Pouvez-vous expliquer pourquoi vous voulez faire de la bulle de tri récursif? Ne semble pas être une bonne idée ...


L'IMHO RESSION n'est vraiment pas utile pour le tri des bulles (pour augmenter sa lisibilité ou sa performance). Fondamentalement, vous changeriez simplement le premier pour en une récursion. recsort (arr, i) {...; Recsort (arr, i ++)} . Qui est assez inutile.


Je veux juste essayer de convertir "n'importe quel" code de l'itération connu en un code récursif équivalent, pour comprendre la récursion meilleure ... Sort de bulle est arrivé d'abord dans mon esprit comme exemple classique de code à base d'itération ... pas d'autre spécifique Raison de choisir une sorte de bulle ...


16 Réponses :


3
votes

Je ne sais pas si BubblesTort est un bon algorithme pour pratiquer la récursion. Il serait assez moche de la convertir en récursivité car c'est un cycle imbriqué. Cela ressemblerait à ceci:

function pass(i,j,n,arr)
{
  if(arr[i]>arr(j))
    swap(arr[i],arr[j]);

  if(j==n)
  {
    j=0;
    i=i+1;
  }
  if(i==n+1)
    return arr;

  return pass(i,j+1,n,arr);
}


2 commentaires

Eh bien, Quicksort a une expression très naturelle en récursivité, mais cela n'a pas "besoin". Vous n'avez jamais "besoin" de récursion, c'est juste que parfois c'est le moyen clair d'écrire quelque chose.


Eh bien ouais, c'est ce que je voulais dire.



2
votes

récursivité est une technique de conception basée sur des preuves inductives. Examine une ou plusieurs base (simples) cas (s) pour votre problème, et une ou plusieurs façons de déplacer le problème plus d'être un problème de base cas. Ensuite, à chaque étape de l'algorithme, vous reconnaissez soit terminé (et traiter de façon appropriée avec un cas de base) rendent le problème un peu plus près d'être un cas de base.

Bubble est en quelque sorte une simple application de l'observation selon laquelle un tableau trié possède toutes les paires adjacentes d'éléments dans l'ordre. Défini récursive, il fonctionne comme:

  1. Cas de base: Il y a un tableau de taille 1 (ou moins) à trier. Il est trié, bien sûr.
  2. Inductive cas: Bubble élément le plus important au début du tableau. Maintenant, il y a un tableau plus petit élément de sorte, qui le font.

    Vous pouvez écrire cette idée dans le langage de programmation de votre choix, et vous obtenez sorte de bulle. Oh, mais vous devez définir ce que signifie « bulle élément le plus important ». Eh bien, c'est une autre occasion pour la conception récursive. Je pense que vous avez l'idée, cependant.

    sortes plus rapides sont principalement basées sur des observations sur la façon dont on se rapproche de l'objectif en moins de travail. tri rapide, par exemple, repose sur l'idée que, si un tableau est trié, puis il y a un élément P, et tous les éléments moins que P sont P de gauche, et tous les éléments plus que P sont à droite de P. Si vous pouvez établir cette propriété sur un tableau, et également choisir P, vous pouvez réduire le problème à peu près la moitié à chaque étape au lieu de simplement par un.


1 commentaires

+1 On "Sort Bubble n'est qu'une application de l'observation qu'un tableau trié a toutes les paires d'éléments adjacents dans l'ordre". Très bien pensé, jamais arrêté de penser à cela avant :-)



10
votes
public void sort(int[] arr, int first, int last){

    if(first < last && last > 0){
        if(arr[first] > arr[first+1]){
            int temp = arr[first];
            arr[first] = arr[first+1];
            arr[first+1] = temp;
        }
        sort(arr, first+1, last);
        sort(arr, first, last-1);
    }
    else
        return;
}
Late for 2 years, but maybe it will useful to someone

3 commentaires

Cher Vadimfromua, tout va bien pour répondre aux anciennes questions Cuz Plus de 2500 utilisateurs ont regardé cela et c'est utile pour les autres.


Merci beaucoup, 3 ans plus tard, et votre réponse est toujours utile. Utilisera votre algorithme pour une classe de 2e semestre de 30 étudiants aujourd'hui :-)


Même plus tard commentaire: Il s'agit d'une version lente extrêmement de la bulle. Vous vous retrouvez avec un tas de sortes redondantes de parties déjà triées de la matrice. Le swap & Tri (arrondie, premier + 1, dernier) doit recenser sans appeler Trier (Arr, premier, Last-1) ON Chaque appel récursif - une seule fois lorsque le "bouillonnement" est terminé.



0
votes

Parce que j'ai trouvé cette question comme l'un des premiers exemples, je voudrais fournir une autre façon de faire la réursion, sans arguments supplémentaires: xxx

de cette manière, nous trierons Toute l'ensemble des casque pour chaque appel.

Pourquoi ça marche? Parce que chaque tri de bulle est exécutée, nous mettrons au moins le plus grand élément à l'indice le plus à droite.
Nous savons que tous les éléments jusqu'à ce que le dernier échange soit dans un état inconnu, tout après le tri des derniers échanges.

implémentations en Java (tableau / liste d'argument-modification / non) peut être trouvé là-bas: https://codereview.stackexchange.com/questions/24006/recursive-bubble-sort -in-java / 24133 # 24133


0 commentaires

0
votes
#include <stdio.h>
#include <stdlib.h>

void sort(int *arr, int first, int last){

    if(first < last && last > 0){
        if(arr[first] > arr[first+1]){
            int temp = arr[first];
            arr[first] = arr[first+1];
            arr[first+1] = temp;
        }
        sort(arr, first+1, last);
        sort(arr, first, last-1);
    }
    else
        return;
}
int main(void) {

    int data [] = { 3, 5 , 6, 2, 1, 10, 4};
    int len = sizeof(data)/sizeof(int);
    int i = 0;
    sort(data,0,len-1);
    for(i=0;i<len;i++)
        printf("%d ",data[i]);

    return EXIT_SUCCESS;
}

0 commentaires

0
votes

Voici ma réponse. C'est essentiellement la même chose que la réponse de Vladimfrromua (variante récursive de tri de bulles), mais au lieu de faire un nombre fixe de pistes, des courses supplémentaires ne sont effectuées que si elles sont détectées que le tableau était réorganisé sur la précédente exécution.

Un autre couple de différences sont ci-dessous: p>

1.Le paramètre indexation du point de départ de la matrice a été supprimé en compensant l'adresse du tableau dans des appels récursifs. 2.Le chèque "si (premier 0)" dans Vlad's ou "si (-P_length == 1)" dans mon code est mieux effectué avant l'appel récursif qui entraînerait la longueur de la matrice 1, Puisqu'il s'agit d'un appel de moins sur la pile. p>

J'ai ajouté du code pour lire l'entrée de la ligne de commande et imprimer les tableaux non acheminés et triés, pour plus de commodité. P>

#include <stdio.h>
#include <stdlib.h>
#include <assert.h>

typedef enum { FALSE, TRUE } boolean_t;

void
swap_int(int *a, int *b) {

    int temp = *a;

    *a = *b;
    *b = temp;
}

boolean_t
sort_array(int p_array[], int p_length) {

    boolean_t result;

    if (p_array[0] > p_array[1]) {
        swap_int(p_array, p_array + 1);
        result = TRUE;
    } else {
        result = FALSE;
    }

    if (--p_length == 1) {
        return result;
    }

    result |= sort_array(p_array + 1, p_length);

    if (result) {
        sort_array(p_array, p_length);
    }

    return result;
}

void
print_array_int(int p_array[], int p_length) {

    int n;

    for (n = 0; n < p_length - 1; n++) {
        printf("%d, ", p_array[n]);
    }

    printf("%d\n", p_array[n]);
}

int
main(int argc, char **argv) {

    int *array;
    int array_length = argc - 1;
    int n;

    array = malloc(array_length * sizeof(*array));

    for (n = 0; n < array_length; n++) {
        sscanf(argv[n + 1], "%d", array + n);
    }

    printf("\nUnsorted array:\n");
    print_array_int(array, array_length);
    sort_array(array, array_length);
    printf("\nSorted array:\n");
    print_array_int(array, array_length);

return 0;
}


0 commentaires

1
votes

voici une abrasive abrasive en JavaScript: xxx

Les 2 premières lignes à l'intérieur de la fonction permettent à l'utilisateur d'appeler bubblesortrecursif (tableau) et la fonction définira Le index1 et index2


0 commentaires

1
votes

Voici un autre moyen facile de trier votre tableau récursivement code> à l'aide de Bubble-tri code>.

static void recursive_bubble_sort(int[] Arr, int l)
{// 'Arr' is the array where 'l' is the length of the array

    if (l == 0) {
       return;
    }

    for (int j = 0; j < l - 1; j++) {
        if (Arr[j] > Arr[j + 1]) {
            swap(Arr[j], Arr[j + 1]);
        }
    }

    recursive_bubble_sort(Arr, l - 1);
}


0 commentaires

-2
votes
Bubble sort: recursive and efficient

public static void bubbleSort(int[] ele, int counter, int index) {
            int temp=-1;
            if (counter < ele.length) {
                if (index < ele.length - 1) {
                    if (ele[index] > ele[index+1]) {
                        ele[index] += ele[index+1];
                        ele[index+1] = ele[index] - ele[index+1];
                        ele[index] = ele[index] - ele[index+1];
                        temp = ele[index];
                    }
                    bubbleSort(ele, counter, index+1);
                    //temp = sortedIndex;
                    return;
                }
                if(counter == ele.length-1 && temp==-1){
                    return;
                }
                bubbleSort(ele, counter+1, 0);
            }

        }

2 commentaires

UM, la tri des bulles est en fait l'une des algorithmes de tri efficaces les plus dans .


Oui c'est le cas :) . Mais nous pouvons le rendre plus efficace qu'en sortant de la boucle lorsqu'il n'y avait aucun swaps s'est produit.



0
votes

Que diriez-vous de ce type de solution:

package recursive.bubble;

public class RecursiveBubble {

    public static boolean sort(int []arr){
        if(!bubbleSorted(arr, 0)){
            return sort(arr);
        }
        return true;
    }
    public static boolean bubbleSorted(int []a,int index){    
        if(a.length<2){
            return true;
        }
        if(index==a.length-2){
            if(a[index+1]<a[index]){
                swap(a,index,index+1);
                return false;
            }
            return true;
        }
        boolean isSorted=false;
        if(a[index]<=a[index+1]){
            isSorted=true;
        }else{
            swap(a,index,index+1);
        }
        return isSorted && bubbleSorted(a, index+1);
    }
    private static void swap(int[] a, int index, int i) {
        int tmp=a[index];
        a[index]=a[i];
        a[i]=tmp;
    }
    public static void main(String[] args) {
        int []a={4,5,6,2,2,3,9,1,8};
        if(sort(a))
        for (int i = 0; i < a.length; i++) {
            System.out.println(a[i]);
        }
    }
}


0 commentaires

0
votes
def bubble_sort(l):
    for i, num in enumerate(l):
        try:
            if l[i+1] < num:
                l[i] = l[i+1]
                l[i+1] = num
                bubble_sort(l)
        except IndexError:
            pass
    return l

0 commentaires

0
votes
#include <stdio.h>
void bubbleSort(int *,int ,int ,int );
void swap(int *, int *);
void printArray(int *,int);

int main()
{
    int n,c;

    printf("Enter number of elements\n");
    scanf("%d", &n);

    int array[n];

    printf("Enter %d integers\n", n);

    for (c = 0; c < n; c++)
        scanf("%d", &array[c]);

    printf("Before Sorting:\n");
    printArray(array,n);

    bubbleSort(array,0,0,n);

    printf("After Soring:\n");
    printArray(array,n);

 }

 void bubbleSort(int *array,int i,int j,int n)
 {
     if(j==n-i-1)
     {
         i = i+1;
         j = 0;
     }
     if(i==n-1)
         return;

     if(array[j]>array[j+1])
         swap(&array[j],&array[j+1]);

     j++;
     bubbleSort(array,i,j,n);
 }

 void swap(int *p,int *q)
 {
     int t = *q  ;
     *q = *p;
     *p = t;
 }

 void printArray(int *array,int n)
 {
     int c=0;
     for (c = 0; c < n; c++)
        printf("%d ", array[c]);
    printf("\n");
 }

0 commentaires

0
votes

Voici le code fonctionnel SCALA. Tout est immuable. Et c'est la récursion de la queue. Donc, la pile devrait être fine xxx


0 commentaires

0
votes

Voici une autre version de récursivité JavaScript avec une syntaxe ES6 / 7, telle que les paramètres d'argument par défaut:

p>

let unsorted = [4, 2, 4, 99, 1, 1, 5];

const bubSort = (arr, end = 0) => {
  // base case
  if (end >= arr.length) {
    return arr;
  }

  // bubble sort, goes through once
  for (let i = 0; i < arr.length - 1; i++) {
    if (arr[i] > arr[i + 1]) {
      // swap!
      let hold = arr[i + 1];
      arr[i + 1] = arr[i];
      arr[i] = hold;
    }
  }

  // down the rabbit hole; updating `end` is a small optimization
  return bubSort(arr, ++end);
}

const sorted = bubSort(unsorted);
console.log(sorted);


0 commentaires

0
votes
package com.examplehub.sorts;

public class BubbleSortRecursion implements Sort {
  @Override
  public void sort(int[] numbers) {
    sortRecursion(numbers, numbers.length);
  }

  /**
   * BubbleSort algorithm implements using recursion.
   *
   * @param numbers the numbers to be sorted.
   * @param length the length of numbers.
   */
  public void sortRecursion(int[] numbers, int length) {
    boolean swapped = false;
    for (int i = 0; i < length - 1; ++i) {
      if (numbers[i] > numbers[i + 1]) {
        int temp = numbers[i];
        numbers[i] = numbers[i + 1];
        numbers[i + 1] = temp;
        swapped = true;
      }
    }
    if (!swapped) {
      return;
    }
    sortRecursion(numbers, length - 1);
  }

  @Override
  public <T extends Comparable<T>> void sort(T[] array) {
    sortRecursion(array, array.length);
  }

  /**
   * Generic BubbleSort algorithm implements using recursion.
   *
   * @param array the array to be sorted.
   * @param length the length of array.
   * @param <T> the class of the objects in the array.
   */
  public <T extends Comparable<T>> void sortRecursion(T[] array, int length) {
    boolean swapped = false;
    for (int i = 0; i < length - 1; ++i) {
      if (array[i].compareTo(array[i + 1]) > 0) {
        T temp = array[i];
        array[i] = array[i + 1];
        array[i + 1] = temp;
        swapped = true;
      }
    }
    if (!swapped) {
      return;
    }
    sortRecursion(array, length - 1);
  }
}
source from

0 commentaires

0
votes

golang: xxx


0 commentaires