jayelm
jayelm

Reputation: 7657

Finding the middle of three numbers

I'm looking for alternative or more concise ways to return the middle of three unique values. What I have right now is a function:

def middle(x, y, z):
    if x > y and x < z:
        return x
    if y > x and y < z:
        return y
    return z

Anything better?

Upvotes: 3

Views: 9109

Answers (6)

hardcode
hardcode

Reputation: 53

for fun:

def middle(x, y, z):
    if x < y:
        if y < z:
            return y
        elif x < z:
            return z
        else:
            return x
    else:
        if x < z:
            return x
        elif y > z:
            return y
        else:
            return z

Upvotes: 1

abarnert
abarnert

Reputation: 365737

Just for fun…

We don't really need to sort all three values; we just need to keep track of the 2 largest as we go through the whole list, right?

In general, this can be useful, so the standard library has a way to do exactly that: the heapq.nlargest function.

def middle(x, y, z):
    return heapq.nlargest(2, (x, y, z))[-1]

In practice, a heap is much slower than sorting a list, so unless the list is pretty big (3 is nowhere near big enough) and the number of elements you need to remember pretty small (2/3rds is nowhere near small enough), this will actually slow you down a lot. As a quick test will show:

In [66]: %timeit heapq.nlargest(2, [1,2,3])[1]
100000 loops, best of 3: 2.78 us per loop

In [67]: %timeit sorted([1,2,3])[1]
1000000 loops, best of 3: 770 ns per loop

So, don't use this here, but keep it in your toolbox for the next time you need the 10 top scores out of 500000.

Upvotes: 1

thefourtheye
thefourtheye

Reputation: 239473

def middle(x, y, z):
    return sorted([x, y, z])[1]

This should return the middle number. But if you actually meant maximum number

def maximum(x, y, z):
    return max([x, y, z])

Edit: As suggested by abarnert in the comments section, instead of y>x and x<z use x < y < z, which is more readable and pythonic.

Upvotes: 9

Stefan
Stefan

Reputation: 528

You can also make some kind of a median function which works not only for 3 values

def median(list): 
    list = sorted(list) 
    if len(list) % 2 == 0: 
        n = len(list)//2 
        return (list[n]+list[n-1])/2 
    else: 
        return list[len(l)//2] 

Upvotes: 0

abarnert
abarnert

Reputation: 365737

With Python 3.4, statistics.median is in the standard library:

import statistics

def middle(x, y, z):
    return statistics.median((x, y, z))

With 3.1-3.3, after you pip install stats:

import stats

def middle(x, y, z):
    return stats.median((x, y, z))

I believe a backport for 2.6-2.7 is in the works, but does not yet exist. (For 2.5 or 3.0, just upgrade already.)

Of course if you had 4 values, you'd have to decide what "middle" means; median would use the mean of the two middle values, but you might want something different.

Upvotes: 3

jayelm
jayelm

Reputation: 7657

def middle(x, y, z):
    return x + y + z - max(x, y, z) - min(x, y, z)

Just for the fun of it.

Upvotes: 2

Related Questions