Bienvenue sur IndexError.

Ici vous pouvez poser des questions sur Python et le Framework Django.

Consultez la FAQ pour améliorer vos chances d'avoir des réponses à vos questions.

Façon pythonique d'obtenir des fenêtres de nombres

+6 votes

Je cherche la meilleur manière d'obtenir des fenêtres de nombre à partir d'une liste non ordonnée de chiffres, de cette manière :

values = [0,3,12,34,5,14,1]
for window in myfunction(values, 10) :
   print window

Ce qui nous donnerait :

[0,1,3,5]
[12,14]
[]
[34]

J'imagine qu'il existe déjà une fonction de ce type, mais je n'ai pas trouvé.

demandé 25-Aou-2015 par Jev (388 points)

C'est quoi que tu appel les fenêtres ? Les regrouper pr dizaines ?

Yep, dans cet exemple là du moins, ça devra être variable.

3 Réponses

+8 votes
 
Meilleure réponse

Personnellement j'utiliserai groupby

Voila ce que ça pourrait donner :

from itertools import groupby

def group_by_window(values, n):
    # On est obligé de trier la liste avant
    sorted_val = sorted(values)
    return groupby(sorted_val, key=lambda e: e//n)

for id_window, vals in myfunction(values, 10) :
    print(id_window, ":", list(vals))

Résultat :

0 : [0, 1, 3, 5]
1 : [12, 14]
3 : [34]
répondu 25-Aou-2015 par Kje (464 points)
sélectionné 25-Aou-2015 par Jev

Si tu veux absolument récupérer uniquement les listes des valeurs et les fenetre vides explicitement, tu devra probablement écrire l'itérateur à la main. Quelque chose comme :

def myfunction(values, n):
    n_max = max(values) // n
    for current in range(n_max+1):
        yield [v for v in values if v // n == current]

Il est possible de faire plus efficace mais tu comprendra l'idée

je m'incline :D

(remarque: il faut prendre range(n_max+1) si tu veux englober tout tes nombres)

Merci, c'est nikel. Je me disais bien qu'on pouvait faire quelque chose avec itertools mais j'avais pas pensé à groupby de cette manière.

en effet, je corrige.

Ça m'apprendra à poster sans tester :p

+1 vote
répondu 25-Aou-2015 par buffalo974 (2,956 points)

Je pense pas que les slices marcheront facilement car il faut connaitre le nombre d'éléments pour les utiliser. Il faudrait a minima trier la liste puis chercher le nombre d'éléments...

0 votes

De ce que je comprends tu veux trier les nombres de ta liste en fonction d'une base donnée en paramètre de ta fonction (ici une base 10).
Dans un premier temps je trierai ta liste avec un values.sort
Ensuite tu boucles sur tes nombres, tu testes s'ils sont inférieurs à ta base*indice et tu classes tes nombres dans une liste de liste en utilisant l'indice:
results[indice] = [liste des nombres < base*indice]

répondu 25-Aou-2015 par furankun (1,434 points)
...