Min and Max of a List in Python (without using min

2019-02-16 02:20发布

I was wondering if there is a way to find min & max of a list without using min/max functions in Python. So i wrote a small code for the same using recursion. My logic is very naive: I make two stacks (min_stack and max_stack) which keep track of minimum and maximum during each recursive call. I have two questions:

  1. Could somebody help me estimate the complexity of my code?
  2. Is there a better way to do this? Will sorting the list using mergesort/quicksort and picking up first and last element give a better performance?

Thank you

Here is my attempt in Python:

minimum = []
maximum = []

# Defining Stack Class
class Stack:
    def __init__(self) :
        self.items = []

    def push(self, item) :
        self.items.append(item)

    def pop(self) :
        return self.items.pop()

    def access(self, index):
        return self.items[index]

    def isEmpty(self) :
        return (self.items == [])

    def length(self):
        return len(self.items)

def minmax(input_list):
    # make two stacks, one for min and one for max
    min_stack = Stack()
    max_stack = Stack()
    # comparing the first two elements of the list and putting them in appropriate stack
    if input_list[0]<input_list[1]:
        min_stack.push(input_list[0])
        max_stack.push(input_list[1])
    else:
        max_stack.push(input_list[0])
        min_stack.push(input_list[1])

    # Pushing remaining elements of the list into appropriate stacks. 
    for i in range(2, len(input_list)):
        if input_list[i] < min_stack.access(-1):
            min_stack.push(input_list[i])
        else:
            max_stack.push(input_list[i])

    # to find minimum
    minlist = []
    while min_stack.length() > 0:
        minlist.append(min_stack.pop())

    # to find maximum
    maxlist = []
    while max_stack.length() > 0:
        maxlist.append(max_stack.pop())

    if len(minlist) > 1:
        minmax(minlist)
    else:
        minimum.append(minlist)


    if len(maxlist) > 1:
        minmax(maxlist)
    else:
        maximum.append(maxlist)

def main():
    input_list = [2, 0, 2, 7, 5, -1, -2]
    print 'Input List is: ', input_list
    minmax(input_list)

print 'Global Minimum is: ', minimum[0]
print 'Global Maximum is: ', maximum[len(maximum)-1]

if __name__ == "__main__":
    main()

2条回答
地球回转人心会变
2楼-- · 2019-02-16 02:41

Using sorted() would, of course, be reliable, quick to write, and high performance for moderate-sized lists because it is built-in. For large lists, an O(n) algorithm would be faster e.g.:

def minmax1 (x):
    # this function fails if the list length is 0 
    minimum = maximum = x[0]
    for i in x[1:]:
        if i < minimum: 
            minimum = i 
        else: 
            if i > maximum: maximum = i
    return (minimum,maximum)

print(minmax1([9,8,7,6,5,4,3,2,1,11,12,13,14,15,16,17,18,19]))
print(minmax1([1]))
print(minmax1([2, 0, 2, 7, 5, -1, -2]))

... for which the output is:

(1, 19)
(1, 1)
(-2, 7)

I was interested to check the performance of the two alternatives. On my PC running Windows XP and Python 3.2.3, I found that the sorting approach is faster than the minmax1() function defined above for lists of fewer than 500 elements but, for longer lists, the O(n) minmax1() is faster. My timing test code was as follows:

def minmax_sort(x):
    x = sorted(x)
    return (x[0],x[-1])

import timeit

aa = list(range(0,100))
a = aa
while (1):
    stime = min(timeit.repeat('minmax_sort(a)', "from __main__ import minmax_sort,a",number=1000))
    mtime = min(timeit.repeat('minmax1(a)', "from __main__ import minmax,a",number=1000))
    if (stime > mtime):
        break
    else:
        a = a + aa
print(len(a))
查看更多
叼着烟拽天下
3楼-- · 2019-02-16 02:53

Finding Min and Max of a list using only recursion.

I had this similar assignment last week and I divided the code into three parts.

Step 1: Finding the minimum value in list

def RecursiveMin(L):
if len(L)==2:
    if L[0]<L[1]:
        return L[0]
    else:
        return L[1]
else:
    X= RecursiveMin(L[1:])
    if L[0]<X:
        return L[0]
    else:
        return X

Step 2: Sorting the list using into ascending order (smallest to largest)

def Sort(x):
L=sorted(x)
if x==L:
    return x
else:
    i=0
    for i in range (len(x)):
        if x[i] > x[i+1] :
            break

    unsortedPart = x[i:]
    R = RecursiveMin(unsortedPart)
    I = unsortedPart.index(R)

    for j in range (len(x)):
        if x[j] > R :
            del x[(I+i)]
            x.insert(j,R)
            break

    return Sort(x)

(I have previously answered a sorting a list question and provided the same code. So please don't flag me for plagiarism since it's my own code Likn: Finding minimum element in a list (recursively) - Python ).

**Step 3: Make a new function with an argument whether the user wants Min value or Max*

def minMax(lst,user):
    if user == min:
       return Sort(lst)
    elif user == max:
       s = Sort(lst)
       return s[::-1]

The last step is not recursive but if you compile all the three steps into one function it will be "1 recursive function". P.S if your question was only about finding the Min and Max in a list you can skip Step 2 and make a few changes to to Step 1 and Step 3

查看更多
登录 后发表回答