Selection sort in Python yields no output - python

I'm trying to run selection sort in python, this is the code that I'm using
def main(list):
input_array = [12, 9, 13, 7, 3, 19, 6, 5]
output_array = selection_sort(input_array)
print(output_array)
def selection_sort(param):
for i in range(0, (len(param) - 1)):
min = i
for j in range(i + 1, len(param)):
if param[min] < param[j]:
min = j
if min != i:
temp = param[i]
param[i] = param[min]
param[min] = temp
return param
The output that I get is
Process finished with exit code 0
I'm using PyCharm as the idea, if that's of any consequence.

input_array should be a list, you are making it a set
input_array = [12, 9, 13, 7, 3, 19, 6, 5]
don't use the variable name list, it is the name for the built-in list
don't use min as a variable name, it is the name for the built-in function min
you don't need an argument for your main method here
you are not calling your main method, call it after the definition of selection_sort
change the line
minimum, i, j, temp = 0
to
minimum, i, j, temp = 0, 0, 0, 0

This will sort in ascending order:
def selection_sort(my_list):
for j in range(len(my_list)):
for i in range(j, len(my_list)):
if my_list[i] < my_list[j]:
my_list[j], my_list[i] = my_list[i], my_list[j]
return my_list
def main():
input_array = [12, 9, 13, 7, 3, 19, 6, 5]
output_array = selection_sort(input_array)
print(output_array)
[3, 5, 6, 7, 9, 12, 13, 19]

Related

Flip half of a list and append it to itself

Im trying to flip half of the elements inside of a list and then spend it onto itself, for example,
if I pass the list [1, 8, 7, 2, 9, 18, 12, 0] into it, I should get [1, 0, 7, 18, 9, 2, 12, 8] out, here is my current code
def flip_half(list):
for i in range(0,len(list)):
if i % 2 != 0:
listflip = list[i]
print(listflip)
return list
You can directly assign slices in python. So if you can determine the slice you want to assign from and to, you can directly change the elements. This assign from every other element in reverse l[::-2] to every other element starting with the second: l[1::2] :
l = [1, 8, 7, 2, 9, 18, 12, 0]
l[1::2] = l[::-2]
print(l)
#[1, 0, 7, 18, 9, 2, 12, 8]
If you wanted to do it in a loop:
def flip_half(list):
out = []
for i in range(0,len(list)):
if i % 2 != 0:
out.append(list[-i])
else:
out.append(list[i])
return out
print(flip_half([1, 8, 7, 2, 9, 18, 12, 0]))
If you need that elements with odd indexes has reverse order then one of next solutions (l - is your list):
Slices
l[1::2] = l[1::2][::-1]
List comprehension
l = [l[i] if i % 2 == 0 else l[-(i + len(l)%2)] for i in range(len(l))]
Function
def flip_half(lst):
res= []
for i in range(len(lst)):
if i % 2 != 0:
res.append(lst[-(i + len(lst) % 2)])
else:
res.append(lst[i])
return res
l = flip_half(l)
Generator function
def flip_half(lst):
for i in range(len(lst)):
if i % 2 != 0:
yield lst[-(i + len(lst) % 2)]
else:
yield lst[i]
l = list(flip_half(l))

How to print out certain elements of a list in python?

So I have a list li = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13] and I only want to print out elements that are a part of an arithmetic sequence 6n - 5 (1st, 7th and 13th).
How can I do that if I have a list with n elements?
You could simply say
print([x for x in li if x % 6 == 1])
or, alternatively, if you just want the sequence and don't want to bother about creating li in the first place,
print([6*n-5 for n in range(1, (13+5)//6+1)])
Use the code:
li = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
new=[]
for i in li:
if int((i+5)/6)==((i+5)/6):
#You can also use
#if ((i+5)/6).is_integer():
new.append(i)
I tried to make it as easy as possible.
Hope it helps :)
li = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
for n in range(1,len(li)+1): #choose n such that it is length of the list since it cant have more values than the number of values in the list.
for i in li:
if (6*n - 5) == i:
print(i)
Hope this helps
Thanks
Michael
From what I understand, you want the elements whose positions are generated by the sequence. Hence, you want elements from an array of length n whose index is from the sequence function 6x-5.
NOTE: I am assuming you are using 1-based indexing, which means, when you say 1st element in your list, you intend to get 1 and not 2.
n = 13
li = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
# generate the sequence till n
seq = []
x = 1
while 6*x-5 <= n:
seq.append(6*x-5)
x += 1
# Print the elements from the sequence:
for idx in seq:
print(li[idx-1])
# If you want to store it in another list:
li2 = [li[idx-1] for idx in seq]
Below is a more generic and efficient way for above code:
n = 13
li = list(range(1, n+1)) # More easy to write
# More efficient way is to create a generator function
def get_seq(n):
x = 1
while 6*x-5 <= n:
yield 6*x-5
x += 1
# Get the generator object
seq = get_seq(n)
# Print the elements from the sequence:
for idx in seq:
print(li[idx-1])
# Want to store it in another list:
seq = get_seq(n) # Don't forget to get a new generator object.
li2 = [li[idx-1] for idx in seq]
Output for both snippets:
1
7
13
Hope the answer helps, and remove confusion for others as well ;)
You can simply generate the sequence for any n.
for example:
n = 10
print([ 6*x - 5 for x in range(1,n)])
output:
[1, 7, 13, 19, 25, 31, 37, 43, 49]
>>> [Finished in 0.2s]
But if you just want to filter your existing list li:
li = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
print([ x for x in li if x % 6 == 1 ])
output:
[1, 7, 13]
>>>
[Finished in 0.3s]
li[1] is 2, li[7] is 8 and the element with the index 13 is out of range.
li = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13]
for num, i in enumerate(li):
if ((num + 5)/6).is_integer():
print(i)
# 2
# 8
If you want to start with the index 1 add start=1 to the enumerate() function.
for num, i in enumerate(li, start=1):
if ((num + 5)/6).is_integer():
print(i)
# 1
# 7
# 13

Give me highest element

I got a list like these:
List1: [1, 5, 9, 1, 5, 9, 15, 21, 29, 1, 5, 9, 15]
I want a new list, which should content the highest number, before it starts again with 1.
List_new: [9, 29, 15]
I tried this:
List_new = []
for i in range(len(List1)):
j = List1[i]
if j + 1 == '1':
List_new += [j]
else:
continue
print(j)
But I got an empty list back.
Simply with built-in only libs:
from itertools import groupby
result = [max(group) for r, group in groupby(your_list, lambda x: x == 1) if not r]
def max_of_sublists(megalist):
maxitem = 0
for item in megalist:
if item == 1 and maxitem:
yield maxitem
maxitem = 0
if maxitem < item:
maxitem = item
yield maxitem
biglist=[1, 5, 9, 1, 5, 9, 15, 21, 29, 1, 5, 9, 15]
print([x for x in max_of_sublists(biglist)])
Your code has a few issues. Here's a version that works.
list1 = [1, 5, 9, 1, 5, 9, 15, 21, 29, 1, 5, 9, 15]
list2 = []
for i in range(len(list1)-1):
if list1[i+1] == 1:
list2.append(list1[i])
list2.append(list1[-1]) # adds the last element
This outputs:
>>> list2
[9, 29, 15]
Here is a simple for loop that will answer your question:
List_new = [List1[0]] # initialize with first element
for i in List1[1:]: # simply iterate over list elements, not indices
if i != 1 and i > List_new[-1]:
List_new[-1] = i # current element is the new maximum
elif i == 1:
List_new.append(i) # encountered a 1, start looking for new maximum
See inline comments for explanations.
This problem can be implemented in a one liner using python modules as in the very elegant solution suggested by Andrey. However, if you would like to follow on the logic, check out this solution.
def max_values_between_ones(numbers):
max_values = []
max_value = None
for i in range(len(numbers)):
if numbers[i] == 1:
if max_value != None:
max_values.append(max_value)
max_value = None
# max_value is None when they were no values != 1 before this 1
else:
if max_value != None:
# this part was missing in your code, to get the max value
# you should be comparing the current value with the max value so far
max_value = max(numbers[i], max_value)
else:
# set max_value to any not 1 value
max_value = numbers[i]
# if the list didn't end with 1, add the last max_value
if max_value != None:
max_values.append(max_value)
return max_values
numbers = [1, 5, 9, 1, 5, 9, 15, 21, 29, 1, 5, 9, 15]
max_values = max_values_between_ones(numbers)
print(max_values)
>> [9, 29, 15]
Like this:
l = [1, 5, 9, 1, 5, 9, 15, 21, 29, 1, 5, 9, 15]
pos = [item for item in range(0, len(l)) if l[item] == 1]
new_list = []
for n in range(len(pos)):
if n != len(pos) - 1:
new_list.append(l[pos[n]:pos[n+1]])
else:
new_list.append(l[pos[n]:])
print map(lambda x: max(x), new_list)
List1 = [1, 5, 9, 1, 5, 9, 15, 21, 29, 1, 5, 9, 15]
maxi = 0
List2 = []
for i in range(0,len(List1)):
if maxi < List1[i]:
maxi = List1[i]
if (i == len(List1)-1 or List1[i] == 1) and maxi > 1:
List2.append(maxi)
maxi = 0
print List2

Multiples of 3 and 5

I am trying to write a program that takes an input number T(number of test cases), and then asks for the numbers N.
This is my code:
T = int(raw_input())
L = [int(raw_input()) for i in range(T)]
L1 = []
for i in range(0,L[i]):
if (i%3 == 0 or i%5 ==0):
L1.append(i)
print L1
Input: 2 10 20
Output: [0, 3, 5, 6, 9, 10, 12, 15, 18]
I would like the output to be of the following format:
[[0, 3, 5, 6, 9], [0, 3, 5, 6, 9, 10, 12, 15, 18]]
Here [0, 3, 5, 6, 9] is the list that has elements with both multiples of 3 and 5 for number 10
[0, 3, 5, 6, 9, 10, 12, 15, 18] is the list that has elements with both multiples of 3 and 5 for number 20
I am new to python. kindly let me know how I should proceed on this.
The following will produce a list of lists containing all the multiples of 3 and 5 that are less than the given number.
L = [10,20]
L1 = []
for i in L:
L2 = [] # initialize a new list
for j in range(i):
if not (j%3 and j%5): # use falsy values and DeMorgan's Law
L2.append(j) # append to this list
if L2: # use this if you don't want to keep empty lists
L1.append(L2)
>>> L1
[[0, 3, 5, 6, 9], [0, 3, 5, 6, 9, 10, 12, 15, 18]]
I think what you want is splitting a list by input values. Hope it helps
num = int(raw_input())
upperBounds= [int(raw_input()) for i in range(num)]
res= []
for upperBound in upperBounds:
res.append([i for i in range(0,upperBound) if not (i % 3 and i % 5)])
output:
2
10
20
[[0, 3, 5, 6, 9], [0, 3, 5, 6, 9, 10, 12, 15, 18]]
This can be easily done by applying appropriate logic:
if the element at index 0 we have to iterate from 0 to that element
else we have to iterate form L[index-1] to L[index]
T = int(raw_input())
L = [int(raw_input()) for i in range(T)]
L1 = []
for j in xrange(len(L)):
temp = []
get = 0 if not j else L[j-1]
# if j==0:
# get = 0
# else:
# get = L[j-1]
for i in range(get, L[j]):
if (i%3 == 0 or i%5 ==0):
temp.append(i)
L1.append(temp)
print L1
>>> [[0, 3, 5, 6, 9], [10, 12, 15, 18]]
Or a more Pythonic and compacted version may look like:
T = int(raw_input())
L = [int(raw_input()) for i in range(T)]
L1 = []
for j in xrange(len(L)):
get = 0 if not j else L[j-1]
L1.append([i for i in range(get, L[j]) if (i%3 == 0 or i%5 ==0)])
print L1
You can simply generate a list of multiples with range(l,u,s) with l the lower bounds, u the upper bound and d the step.
Now if we want to generate multiples of i for a given range, we can use the following function:
def multiples(factor, lower, upper) :
return set(range(lower+(factor-lower)%factor,upper,factor))
We thus manipulate the lower bound as lower+(factor-lower)%factor in order to search - in constant time - the first multiple that is greater than or equal to lower.
Next we need to multiples of 3 and 5:
def multiples35(lower, upper):
return sorted(list(multiples(3,lower,upper)|multiples(5,lower,upper)))
Now we only need to iterate over the list of values and generate the list of multiples for each two numbers:
def func(B):
return [multiples35(0,upper) for upper in B]
Or as full code:
import sets
def multiples(factor, lower, upper) :
return set(range(lower+(factor-lower)%factor,upper,factor))
def multiples35(lower, upper):
return sorted(list(multiples(3,lower,upper)|multiples(5,lower,upper)))
def func(B):
return [multiples35(0,upper) for upper in B]
The main function reads then:
T = int(raw_input())
B = [int(raw_input()) for i in range(T)]
print func(B)

Heap sort Python implementation

def heap_sort(nos):
global size
size = len(nos)
print "the size of the List is : %d " %size
Build_heap(size,nos)
for i in range(size-1,0,-1):
nums[0],nums[i] = nums[i],nums[0]
size = size-1
print "\n", nums
heapify(nos,i,size)
print "heap sort array:" ,nums
def left_child(i):
return 2*i+1
def right_child(i):
return 2*i+2
def heapify(nums,i,size):
l = left_child(i)
r = right_child(i)
if l <= size and r <= size:
if r != size:
if nums[l] >= nums[r]:
max = nums[l]
max_index = l
elif nums[l] <= nums[r]:
max = nums[r]
max_index = r
if nums[i] >= max:
print nums
return
elif nums[i] <= max:
nums[i],nums[max_index] = max,nums[i]
heapify(nums,max_index,size)
else:
nums[i],nums[l] = nums[l],nums[i]
print nums
# build a heap A from an unsorted array
def Build_heap(size,elements):
iterate = size//2-1
for i in range(iterate,-1,-1):
print "In %d iteration" %i
heapify(elements,i,size)
print "heapified array is : " ,elements
if __name__ == '__main__':
#get input from user
nums = [6,9,3,2,4,1,7,5,10]
#sort the list
heap_sort(nums)
Output which I get is something like this:
the size of the List is : 9
In 3 iteration
[6, 9, 3, 10, 4, 1, 7, 5, 2]
In 2 iteration
[6, 9, 7, 10, 4, 1, 3, 5, 2]
In 1 iteration
[6, 10, 7, 9, 4, 1, 3, 5, 2]
[6, 10, 7, 9, 4, 1, 3, 5, 2]
In 0 iteration
[10, 6, 7, 9, 4, 1, 3, 5, 2]
[10, 9, 7, 6, 4, 1, 3, 5, 2]
[10, 9, 7, 6, 4, 1, 3, 5, 2]
heapified array is : [10, 9, 7, 6, 4, 1, 3, 5, 2]
heap sort array:
[9, 7, 6, 4, 1, 3, 5, 2, 10]
I tried implementing a heap sort algorithm in python. The final output is not sorted. There is something wrong in the heapify operation which I tried to figure out, but I couldn't find it.
Can someone point out what's wrong in my code and propose a solution for it?
The first item(0) was swaped with the last item. To keep max-heap invairant, you should call heapify with 0.
def heap_sort(nos):
size = len(nos)
build_heap(size,nos)
for i in range(size-1,0,-1):
nums[0],nums[i] = nums[i],nums[0]
size -= 1
heapify(nos, 0, size) # <--- i -> 0
The following is my PYTHON implementation. If the program is "heapsort.py", an example to run it is "python heapsort.py 10", to sort 10 randomly generated numbers.
The validation code is near the end of the program, to verify the correctness of the function, heapsort().
#!/bin/python
#
# TH #stackoverflow, 2016-01-20, HeapSort
#
import sys, random
def pushdown( A, root, size_of_A ):
M = root * 2
if(M <= size_of_A):
if(size_of_A > M):
if(A[M - 1] < A[M]):
M += 1
if(A[root - 1] < A[M - 1]):
A[root - 1], A[M - 1] = A[M - 1], A[root - 1]
pushdown(A, M, size_of_A)
def heapsort( H ):
for i in range(len(H)/2, 0, -1):
pushdown(H, i, len(H))
for i in range(len(H) - 1, 0, -1):
H[i], H[0] = H[0], H[i]
pushdown(H, 1, i)
return H
number_to_numbers = int(sys.argv[1])
X = [ random.randint(0, number_to_numbers) for i in range(number_to_numbers) ]
Y = X
print Y
print heapsort(X)
print sorted(Y)

Categories

Resources