2016-08-16 1 views
1

J'ai une liste de données transférées cumulatives par lien et périodes au début et à la fin du transfert de données. En d'autres termes, les éléments de times sont des périodes de jours; éléments de data sont la somme des toutes données transférées par ce lien à la fin du transfert en cours:Comment convertir des données cumulées en données quotidiennes?

data = [0.85, 1.6, 1.85, 2.89, 3.56, 4.05, 5.56, 7.89] 
times = [[0.5, 1.3], [1.8, 2.1], [2.9, 2.99], [3.5, 3.59], [3.6, 4.1], [4.2, 4.35], [4.65, 4.76], [4.85, 5.5]] 

est-il un moyen python ou numpy comment puis-je convertir les données cumulatives des statistiques quotidiennes ([0, 1], [1, 2], [2, 3], [3, 4,], [4, 5], [5, 6]) des données transférées ?

P.S Les données quotidiennes signifie combien de données ont été transférées en particulier entre 0 et 1 période (1 et 2 et ainsi de suite). Par exemple, je veux trouver des données transférées entre 0 jour et 1 jour. Au cours de la période [0.5, 1.3]0.85 GB des données ont été transférées. Donc je dois trouver une part de 0.85 GB qui a notamment été transférée entre [0, 1].
0.85 GB * (1-0.5) days/(1.3-0.5) days = 0.53 GB Et ainsi de suite.

+0

Qu'est-ce que "tous les jours" signifie ici? – Divakar

+0

Alors, quel est le résultat attendu pour l'exemple de cas? – Divakar

+0

@Divakar mis à jour à nouveau –

Répondre

1

Vous pouvez utiliser np.split pour segmenter les données dans des tableaux quotidiens. D'abord vous avez besoin des indices qui définissent les bords de chaque jour; Pour cela, vous pouvez utiliser np.histogram où vous définissez les intervalles qui représentent les bords de vos jours. Puis cumsum pour obtenir les indices des bords de chaque jour. Chunked devrait maintenant être une liste de tableaux où chaque tableau contient la valeur pour chaque jour. Vous pouvez appliquer n'importe quelle fonction réductrice que vous voulez pour cela.

print(chunked) 
# [array([0.85]), array([1.6, 1.85]), ...] 

map(np.sum, chunked) 

Notez que les tableaux de temps/valeurs doivent être triés pour que la division fonctionne.

...

Plus lisible, mais beaucoup plus lent, vous pouvez sélectionner des données pour chaque jour.

days = np.floor(times) 
chunked = [data[days == day] for day in range(5)] 
+0

Est-il possible de considérer le fait que certains transferts ont commencé à '0' jour et se terminent à' 1' jour? –

+0

Je ne sais pas comment vous le feriez de manière numérique. Mais votre question va dans une direction qui est très particulière à la tâche que vous voulez résoudre (c'est-à-dire qui n'est pas utile aux autres utilisateurs de SO). Vous devriez obtenir un stylo et du papier et trouver une solution, puis vous pouvez demander comment optimiser un code lent avec numpy. – csiz

1

IIUC vous pouvez faire soomething comme ça -

lims = np.arange(data.size)+1 
col0 = lims - times[:,0] 
col1 = times[:,1] - lims 
lens = times[:,1] - times[:,0] 

out = data*col0/lens 
shares = data*(col1/lens) 
out[1:] += shares.cumsum()[:-1] 

run Exemple -

In [144]: data 
Out[144]: array([ 0.85, 1.6 , 1.85, 2.89, 3.56, 4.05, 5.56, 7.89]) 

In [145]: times 
Out[145]: 
array([[ 0.5 , 1.3 ], 
     [ 1.8 , 2.1 ], 
     [ 2.9 , 2.99], 
     [ 3.5 , 3.59], 
     [ 3.6 , 4.1 ], 
     [ 4.2 , 4.35], 
     [ 4.65, 4.76], 
     [ 4.85, 5.5 ]]) 

In [146]: out 
Out[146]: 
array([ 0.53125 , 1.38541667, 2.90763889, 16.70208333, 
     -2.55102778, 29.67297222, 55.3047904 , -138.46269211]) 
+0

Premier élément est correct ...mais d'autres comme 118, 38, 16, 48 uhhh –

+0

@RomaKarageorgievich Expliquez le résultat attendu pour le second élément de votre exemple de cas? – Divakar

+0

combien de données sont transférées entre '1' et' 2'. Nous avons donc deux périodes [0.5, 1.3] et [1.8, 2.1]. Un partage du premier intervalle est '0,85 * (1,3-1)/(1,3-0,5)' et le partage du second intervalle est '1,6 * (2-1,8)/(2,1 - 1,8)'. Est égal à 1,3854 GB' –

1

@Divakar a déjà posté la solution numpy correcte, voici simple python un:

import math 
data = [0.85, 1.6, 1.85, 2.89, 3.56, 4.05, 5.56, 7.89] 
times = [0.5, 1.3, 1.8, 2.9, 3.5, 3.6, 4.2, 4.65] 
daily = [0] * 7 

for i, t in enumerate(times): 
    daily[int(math.floor(t))] += data[i] 

print daily