Explicación del código de la mediana

Mi profesor escribió esta función mediana y no la entiendo muy bien. ¿Alguien puede explicar la parte sobre i = len(list)/2 y median = avg() y else ¿declaración?

def avg_list(numbers):  
    sum = 0 
    for num in numbers:
        sum += num

    avg = float(sum)/len(numbers)
    print avg

def median(list):            
    list.sort()
    if len(list)%2 == 0:
        #have to take avg of middle two
        i = len(list)/2
        median = avg()
    else:
        #find the middle (remembering that lists start at 0)
        i = len(list)/2
        median = list        
    return median

Para agregar de un ejemplo que vi, para una longitud uniforme de la lista:

def median(s):
    i = len(s)
    if not i%2:
        return (s[(i/2)-1]+s[i/2])/2.0
    return s[i/2]

Esto funciona muy bien pero no entiendo el último return s[i/2]?

Para una longitud de lista impar:

x = [1,2,5,2,3,763,234,23,1,234,21,3,2134,23,54]
median = sorted(x)[len(x)/2]

Como x tiene una longitud de lista impar, ¿no sería el [len(x)/2] ¿Ser un índice de número flotante? ¿No estoy entendiendo todo esto? Cualquier explicación mejor que la mía es muy apreciada.

preguntado el 28 de septiembre de 11 a las 05:09

este código me parece incorrecto. -

marque la tarea como tal. gracias. -

@samack: No está claro is tarea. Comprender lo que ha escrito tu profesor no es lo mismo que que te pidan que lo explique en una tarea ... No veo nada malo en esta pregunta. -

len(x)/2 devuelve un número entero, ya que ambos len(x) y 2 son ints. -

@eryksun mis disculpas por no usar el operador '//', solo he estado haciendo esto durante 3 semanas. -

4 Respuestas

Por qué esto está muy mal, línea por línea:

def median(list):              # 1

    list.sort()                # 2

        if len(list)%2 == 0:   
        #have to take avg of middle two
            i = len(list)/2    # 3
            median = avg()     # 4
        else:
            #find the middle (remembering that lists start at 0)
            i = len(list)/2    # 5
            median = list      # 6

        return median

#1: Es una mala idea dar a sus variables el mismo nombre que los tipos de datos, es decir list.

#2: list.sort() modificará la lista que se está pasando. Uno esperaría un getter como median() no hacer eso

#4 Llama a una función avg() sin argumentos, lo cual no tiene ningún sentido, incluso si se definió dicha función.

#3 y #5 se calculan de la misma manera independientemente de la if rama tomada. A pesar de todo, i nunca se usa

#6 Establece median al original list, que no tiene ningún sentido.


Así es como reescribiría esto (mientras mantengo la claridad):

def median(alist):

    srtd = sorted(alist) # returns a sorted copy
    mid = len(alist)/2   # remember that integer division truncates

    if len(alist) % 2 == 0:  # take the avg of middle two
        return (srtd[mid-1] + srtd[mid]) / 2.0
    else:
        return srtd[mid]

También el avg_list() función (que no se usa ni podría usarse en median()) podría reescribirse como:

def avg_list(numbers):  
    return float(sum(numbers))/len(numbers)

sum() es una función que devuelve la suma de todos los elementos en un iterable.

Respondido el 28 de Septiembre de 11 a las 10:09

helluva gracias a ti! Gracias por la increíble explicación y educación :) - Gg

NullUserException ఠ_ఠ Probé que su código se veía perfecto pero obtengo un error al ingresar 3 y 6 TypeError: los índices de lista deben ser enteros, no flotantes - user1021335

Si está utilizando Python 3 (o from __future__ import division), entonces len(alist)/2 es una división de punto flotante; Usar división de enteros len(alist)//2 en lugar de - Anaphory

Nos falta algo de código aquí, pero podemos descifrarlo.

Los comentarios aquí son instructivos. Cuando comprobamos:

    if len(list)%2 == 0:

Luego, verificamos si la lista tiene la misma longitud. Si una lista tiene un número par de miembros, entonces no hay un verdadero elemento "intermedio", por lo que:

    #have to take avg of middle two
        i = len(list)/2
        median = avg()

Suponemos que la función avg () devolverá el promedio de los dos elementos del medio. Dado que no incluyó una definición de una función avg, es posible que se suponga que esta sea realmente una función avg_list que toma los dos elementos del medio de la lista.

Ahora, si la lista tiene una longitud impar, hay un elemento intermedio, por lo que:

    else:
        #find the middle (remembering that lists start at 0)
        i = len(list)/2
        median = list

Ahora, esto también me parece un poco incorrecto, pero supongo que la intención es que se lea:

median = list[i]

Seríamos nosotros devolviendo el elemento central de la lista. Dado que la lista ha sido ordenada, ese elemento del medio es la verdadera mediana de la lista.

¡Espero que esto ayude!

Respondido el 28 de Septiembre de 11 a las 09:09

Cuando dices, asumimos que la función avg () devolverá el promedio de los dos elementos del medio. ¿Dónde viste eso? ¿Cómo sugiere alguna parte de este programa que está eligiendo los dos números del medio y dividiendo? Gracias por tu explicación sobre el resto ... ¡ayudó mucho! - Gg

GG: Para ser claro, cuando digo "asumimos", eso es literal: lo estoy asumiendo, porque una definición estándar de la mediana de un número par de elementos es la media de los dos elementos del medio. Pero como se señaló en un comentario anterior, avg () no es una función definida aquí y, por lo tanto, este no es un código legal. - Ratzkewatzke

Estoy seguro de que lo dijo en serio como avg_list (), creo. - Gg

Estoy seguro que es tratando de para decir: "Si la lista es de tamaño impar, simplemente tome el elemento central; de lo contrario, tome la media de la Dos elementos ", pero no veo que ese sea el código Realmente haciendo en absoluto.

En particular:

  • Está llamando a un avg() función (no avg_list, nota) pero sin argumentos
  • Está ignorando el valor de i después de calcularlo de la misma manera en ambas ramas

¿Estás seguro de que ese es el código completo que es significó ¿trabajar?

Respondido el 28 de Septiembre de 11 a las 09:09

Para todos ... literalmente, copié y pegué lo que mi profesor escribió para que lo saliéramos y no pude entenderlo ya que omitió todo lo que ustedes mencionaron. Esto es tarea, sí. No estoy pidiendo respuestas, solo explicaciones. Solo le di a mi profesor el beneficio de la duda, él sabía lo que estaba haciendo. Supongo que no ... - Gg

También puede decidir devolver siempre el promedio del subarreglo medio de la lista ordenada: Por ejemplo, devolver el promedio de [4,5] de [1,2,3,4,5,6,7,8] , y el de [5] de [1,2,3,4,5,6,7,8,9].

Una implementación de Python sería:

def median(a):
    ordered = sorted(a)
    length = len(a)
    return float((ordered[length/2] + ordered[-(length+1)/2]))/2

Respondido el 15 de junio de 12 a las 09:06

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.