Bubble sort

Back to General discussions forum

ThereAreNoUsernamesLeftForMe     2024-06-08 20:09:50

Hi there. I am a bit confused about this problem. I have looked through the other posts on the forum about it but I am still not getting it.

My function below does sort the input array as needed, but I don't understand what we need to caclulate for passes. At first I thought it was the number of times an pair is not switched. Then I realized it was the number of times all elements in asubarray was not switched (I think), and I tried to apply this to my code, but I can't seem to get it. I don't understand why my below code is not giving the correct value for passed when the example input data is used ([3, 1, 4, 1, 5, 9, 2, 6]).

def bub_sort(arr):

"""Takes an array of numbers and sorts them in non-decreasing order,
    return the number of passes (When nothing in the current subarray is swapped)
    and the number of swaps made in total"""

passes = 0
total_swaps = 0

# Use for loop to run while loop for each wanted value of k
for k in range(1,len(arr)):
    j = 0
    current_array_swaps = 0
    # Checks every pair (including previous pairs after a switch) in each sublist of arr 
    while j < k:

        current_left = arr[k-j-1]
        current_right = arr[k-j]

            # Second element larger

        if current_right >= current_left:
            j+=1

        else:
             # Switch elements

            arr[k-j] = current_left
            arr[k-j-1] = current_right
            total_swaps += 1
            current_array_swaps +=1
            j+=1

# If no swaps when go through all of current subarray, we add to pass

        if current_array_swaps == 0:
            passes += 1

print(arr,passes,total_swaps)
zelevin     2024-06-08 20:38:54

There are a few issues with the code above.

  1. Your outer loop is not processing the whole list;
  2. Your inner loop is working backwards through the list, meaning the largest number will not bubble up through the list, which sort of defeats the main point of the algorithm.

Perhaps the wikipedia article on the algorithm (and, in particular, the step-by-step example) could be helpful?

ThereAreNoUsernamesLeftForMe     2024-06-08 22:33:04

Thank you, the step by step example was very useful. I have the code working perfectly now.

ThereAreNoUsernamesLeftForMe     2024-06-08 22:59:15

Would I be able to get some more help?

def bub_sort(arr):

    not_swapped = 0
    swapped = 0
    passes = 0
    while True:
        for index,num in enumerate(arr[:-1]):

            if num > arr[index+1]: 
                arr[index],arr[index+1] = arr[index+1],arr[index]
                swapped +=1
            else:
                not_swapped += 1

        passes += 1

        # Seeing if no swaps in entrie array 
        if not_swapped == len(arr)-1:
            break
        else:
            not_swapped = 0


    return(arr,passes,swapped)

So I made the above code. It was correct for the example input data [3, 1, 4, 1, 5, 9, 2, 6]. I then tried the problem data [20, 16, 17, 4, 12, 1 ,5 ,19, 7, 10, 13, 6, 9, 11 ,15, 14, 3 ,2, 21, 8, 18] and my passes was one off, I had 18, the answer was 17. I couldn't see anything wrong with my code, so I passed throuhg another of the problem data for more numbers [6 ,18, 10 ,16 ,3 ,19 ,5 ,21, 7, 4 ,2 ,8 ,9, 12, 17 ,20, 13 ,11, 1 ,14, 15]. This was correct, and I can't seem to figure out why. It seems my passes is correct sometimes but not all the time.

zelevin     2024-06-09 00:31:25

At a quick glance, I don't see anything glaringly wrong (there are a few breaks with good coding practices, such as not_swapped being set to zero in two different spots, but that shouldn't give you a wrong count).

One things that is instantly alarming, though, is changing the iterable (arr) while iterating over it. Perhaps replace the iteration over the list with iterating over just the index?

ThereAreNoUsernamesLeftForMe     2024-06-10 12:24:02

I don't think I am changing arr when ittertating over it. In python I thought that taking a sliced version of list creates a new list in itself. So my intention was to itterate over the new list arr[:-1], which goes up to the last element of arr. Then apply bubble sort if needs be.

Do you thing I should spend more time trying to figure out why my code is not working for [20, 16, 17, 4, 12, 1 ,5 ,19, 7, 10, 13, 6, 9, 11 ,15, 14, 3 ,2, 21, 8, 18], or just contitnue with the other problems?

zelevin     2024-06-10 13:17:58
taking a sliced version of list creates a new list in itself

This statement is correct. This is also the cause of your bug. Do you see that you swap the numbers in the original list, but iterate over the copy?

I'll leave it at that for now. Let me know if you need more hints. Yes, I think you should absolutely continue working on this.

ThereAreNoUsernamesLeftForMe     2024-06-10 15:41:02

I got it working. And I think I understand the issue now. I thought that the subarry arr[:-1] would also update as I change arr. But it is a completly different list in memory, so I was checking the wrong number at times, and since the program would keep running until I got the correct array order I would have a different value for passes sometimes.

ThereAreNoUsernamesLeftForMe     2024-06-10 15:41:17

Thank you for the help :)

Please login and solve 5 problems to be able to post at forum