2009-11-23 7 views
1

Je dois créer un tableau de nombres dans une plage, par exemple:Distribution de la gamme dans le tableau

[1..5] en 10 fois = [1,1,2,2,3,3,4, 4,5,5]

[1..5] à 5 fois = [1,2,3,4,5]

[1..5] en 3 fois = [1,3, 5]

def distribute(start_value, end_value, times, is_integer) 
    array = Array.new(times-1) 

    min_value = [end_value,start_value].min 
    max_value = [end_value,start_value].max 

    if max_value-min_value<times 
     factor = (max_value-min_value).abs/(array.size).to_f 
    else 
     factor = (max_value-min_value).abs/(array.size-1).to_f 
    end 

    for i in 0..array.size 
     v = [ [max_value, factor*(i+1)].min, min_value].max 
     is_integer ? array[i] = v.round : array[i] = v 
    end 

    start_value < end_value ? array : array.reverse 
    end 

distribuer (1, 5, 10, true) => [1, 1, 1, 2, 2, 3, 3, 4, 4, 4 ] #WRONG devrait être [1,1,2,2,3,3,4,4,5,5]

distribuer (5, 1, 5, vrai) => [5, 4, 3, 2, 1] #ok

distribuer (1, 5, 3, true) => [4, 5, 5] #WRONG devrait être [1, 3, 5]

Répondre

0

juste une petite correction ... lorsque le array_size est 0

def distribute(start_value, end_value, array_size, want_ints) 
    diff = 1.0 * (end_value - start_value) 
    n = [array_size-1, 1].max 

    (0..(array_size-1)).map { |i| 
     v = start_value + i * diff/n 
     want_ints ? v.round : v 
    }  
    end 
+1

Plutôt que de compliquer l'algorithme pour le cas particulier, vous pouvez court-circuiter la méthode: 'return [] sauf array_size> 0'. Au moins pour moi, il est plus facile de comprendre le code de cette façon. – FMc

5

How « bout ceci:

def distribute(min,max,items) 
    min,max = [min,max].sort 
    (0...items).map {|i| (min + i * (max - min)/(items-1.0)).round} 
end 

Ou si vous avez vraiment besoin le drapeau int/flotteur:

def distribute(min,max,items,ints) 
    min,max = [min,max].sort 
    a = (0...items).map {|i| min + i * (max - min)/(items-1.0)} 
    ints ? a.map {|i| i.round} : a 
end 

Et si vous avez vraiment besoin de cela pour aller dans le sens inverse si les paramètres vous sont donnés en arrière:

def distribute(min,max,items,ints) 
    usemin,usemax = [min,max].sort 
    diff = usemax - usemin 
    a = (0...items).map {|i| usemin + i * diff/(items-1.0)} 
    a.map! {|i| i.round} if ints 
    min != usemin ? a.reverse : a 
end 
+0

Et évidemment, vous pouvez omettre le min, max = partie si vous savez que vous obtenez les paramètres dans le bon ordre ... –

+0

Peut-être que je ne comprends pas le problème, mais cette réponse ne semble pas fonctionner correctement pour la deuxième OP cas d'utilisation: 'distribute (5, 1, 5, true) => [5, 4, 3, 2, 1]'. – FMc

+0

True. Je viens d'ajouter une autre variation avec ce cas. –