good writing in Ruby...

Discussion in 'Ruby' started by Josselin, Aug 10, 2006.

  1. Josselin

    Josselin Guest

    I know I can write it the 'ugly common way' (loop)
    but I'd like to see how it can be done the Ruby way ... (I am a newbie...)

    here is an array
    roles = [ "a", "b", "c", "d", "e" ]

    Depending upon a variable 'user.role',
    I would like to suppress all elements in the array , less or equal to
    this variable

    ex :
    user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a" deleted
    user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b" deleted
    user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c" deleted
    user.role = "d" #=> roles = [ "e" ] "a", "b", "c", "d" deleted
    user.role = "e" # do nothing

    thanks for your tips

    Joss
    (I am on my way to buy the Ruby Recipes PDF Cookbook...)
     
    Josselin, Aug 10, 2006
    #1
    1. Advertising

  2. On 10.08.2006 18:17, Josselin wrote:
    > I know I can write it the 'ugly common way' (loop)
    > but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >
    > here is an array
    > roles = [ "a", "b", "c", "d", "e" ]
    >
    > Depending upon a variable 'user.role',
    > I would like to suppress all elements in the array , less or equal to
    > this variable
    >
    > ex :
    > user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a" deleted
    > user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b" deleted
    > user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c"
    > deleted
    > user.role = "d" #=> roles = [ "e" ] "a", "b", "c",
    > "d" deleted
    > user.role = "e" # do nothing
    >
    > thanks for your tips
    >
    > Joss
    > (I am on my way to buy the Ruby Recipes PDF Cookbook...)
    >


    Do you actually want to modify the array or do you just want to work
    with the reduced set? Does this help?

    >> roles = %w{a b c d e f}

    => ["a", "b", "c", "d", "e", "f"]
    >> roles.select {|r| r >= "c"}

    => ["c", "d", "e", "f"]
    >> roles.select {|r| r > "c"}

    => ["d", "e", "f"]
    >> roles

    => ["a", "b", "c", "d", "e", "f"]
    >> roles.delete_if {|r| r <= "c"}

    => ["d", "e", "f"]
    >> roles

    => ["d", "e", "f"]

    Kind regards

    robert
     
    Robert Klemme, Aug 10, 2006
    #2
    1. Advertising

  3. > I know I can write it the 'ugly common way' (loop)
    > but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >
    > here is an array
    > roles = [ "a", "b", "c", "d", "e" ]
    >
    > Depending upon a variable 'user.role',
    > I would like to suppress all elements in the array , less or equal to this
    > variable
    >
    > ex :
    > user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a"
    > deleted
    > user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b"
    > deleted
    > user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c"
    > deleted
    > user.role = "d" #=> roles = [ "e" ] "a",
    > "b", "c", "d" deleted
    > user.role = "e" # do nothing


    Maybe...

    roles = roles.map {|x| x <= user.role ? x : nil }.compact

    haven't tested it though...
     
    Philip Hallstrom, Aug 10, 2006
    #3
  4. On Aug 10, 2006, at 11:20 AM, Josselin wrote:

    > Depending upon a variable 'user.role',
    > I would like to suppress all elements in the array , less or equal
    > to this variable
    >
    > ex :
    > user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a" deleted
    > user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b" deleted
    > user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c" deleted
    > user.role = "d" #=> roles = [ "e" ] "a", "b", "c", "d"
    > deleted
    > user.role = "e" # do nothing


    See if this gives you some ideas:

    >> class User
    >> def initialize
    >> @roles = %w[a b c d e]
    >> @role = nil
    >> end
    >>

    ?> attr_accessor :role
    >>

    ?> def roles
    >> return @roles if @role.nil? or not (i = @roles.index(@role))
    >>

    ?> @roles[0...i]
    >> end
    >> end

    => nil
    >> user = User.new

    => #<User:0x322b00 @role=nil, @roles=["a", "b", "c", "d", "e"]>
    >> user.roles

    => ["a", "b", "c", "d", "e"]
    >> user.role = "c"

    => "c"
    >> user.roles

    => ["a", "b"]

    James Edward Gray II
     
    James Edward Gray II, Aug 10, 2006
    #4
  5. Josselin

    Paolo Negri Guest

    Some more infos about what are the relations among the User class and
    the roles array would be nice.

    Anyway you can easily rewrite your role= method of the User class to
    something like this

    def role=(value, array)
    self.role = array.delete value if array.member? value
    end

    or, if you are happy to end up with a role of nil in case the role is
    invalid/already given away

    def role=(value, array)
    self.role = array.delete value
    end


    On 10/08/06, Josselin <> wrote:
    > I know I can write it the 'ugly common way' (loop)
    > but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >
    > here is an array
    > roles = [ "a", "b", "c", "d", "e" ]
    >
    > Depending upon a variable 'user.role',
    > I would like to suppress all elements in the array , less or equal to
    > this variable
    >
    > ex :
    > user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a" deleted
    > user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b" deleted
    > user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c" deleted
    > user.role = "d" #=> roles = [ "e" ] "a", "b", "c", "d" deleted
    > user.role = "e" # do nothing
    >
    > thanks for your tips
    >
    > Joss
    > (I am on my way to buy the Ruby Recipes PDF Cookbook...)
    >
    >
    >
     
    Paolo Negri, Aug 10, 2006
    #5
  6. Josselin wrote:
    > I know I can write it the 'ugly common way' (loop)
    > but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >
    > here is an array
    > roles = [ "a", "b", "c", "d", "e" ]
    >
    > Depending upon a variable 'user.role',
    > I would like to suppress all elements in the array , less or equal to
    > this variable
    >
    > ex :
    > user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a" deleted
    > user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b" deleted
    > user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c"
    > deleted
    > user.role = "d" #=> roles = [ "e" ] "a", "b", "c",
    > "d" deleted
    > user.role = "e" # do nothing


    I'm not quite sure I understand your problem. Is this what you're
    looking for?

    roles = %w{a b c d e}
    user.role = "c"

    # non-destructive:
    roles.select{|role| role > user.role } #=> ["d", "e"]
    roles #=> ["a", "b", "c", "d", "e"]

    # destructive:
    roles.delete_if{|role| role <= user.role }
    roles #=> ["d", "e"]


    Cheers,
    Daniel
     
    Daniel Schierbeck, Aug 10, 2006
    #6
  7. Josselin

    Chad Perrin Guest

    On Fri, Aug 11, 2006 at 01:20:08AM +0900, Josselin wrote:
    > I know I can write it the 'ugly common way' (loop)
    > but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >
    > here is an array
    > roles = [ "a", "b", "c", "d", "e" ]


    Do the "roles" have to be those letters, or did you just use them to
    illustrate what you're doing? If you can use numbers for "roles"
    instead, a whole new realm of possibilities opens up using comparison
    operators.

    --
    CCD CopyWrite Chad Perrin [ http://ccd.apotheon.org ]
    Ben Franklin: "As we enjoy great Advantages from the Inventions of
    others we should be glad of an Opportunity to serve others by any
    Invention of ours, and this we should do freely and generously."
     
    Chad Perrin, Aug 10, 2006
    #7
  8. Chad Perrin wrote:
    > On Fri, Aug 11, 2006 at 01:20:08AM +0900, Josselin wrote:
    >> I know I can write it the 'ugly common way' (loop)
    >> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >>
    >> here is an array
    >> roles = [ "a", "b", "c", "d", "e" ]

    >
    > Do the "roles" have to be those letters, or did you just use them to
    > illustrate what you're doing? If you can use numbers for "roles"
    > instead, a whole new realm of possibilities opens up using comparison
    > operators.


    Actually,

    "b" > "a" => true
    "a" < "b" => true
    "a" <=> "b" => -1


    Cheers,
    Daniel
     
    Daniel Schierbeck, Aug 10, 2006
    #8
  9. Josselin

    Chad Perrin Guest

    On Fri, Aug 11, 2006 at 06:00:13AM +0900, Daniel Schierbeck wrote:
    >
    > Actually,
    >
    > "b" > "a" => true
    > "a" < "b" => true
    > "a" <=> "b" => -1


    Silly me, I forgot Ruby did that.

    --
    CCD CopyWrite Chad Perrin [ http://ccd.apotheon.org ]
    "It's just incredible that a trillion-synapse computer could actually
    spend Saturday afternoon watching a football game." - Marvin Minsky
     
    Chad Perrin, Aug 11, 2006
    #9
  10. Josselin

    Josselin Guest

    On 2006-08-10 22:56:32 +0200, Daniel Schierbeck
    <> said:

    > Chad Perrin wrote:
    >> On Fri, Aug 11, 2006 at 01:20:08AM +0900, Josselin wrote:
    >>> I know I can write it the 'ugly common way' (loop)
    >>> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >>>
    >>> here is an array
    >>> roles = [ "a", "b", "c", "d", "e" ]

    >>
    >> Do the "roles" have to be those letters, or did you just use them to
    >> illustrate what you're doing? If you can use numbers for "roles"
    >> instead, a whole new realm of possibilities opens up using comparison
    >> operators.

    >
    > Actually,
    >
    > "b" > "a" => true
    > "a" < "b" => true
    > "a" <=> "b" => -1
    >
    >
    > Cheers,
    > Daniel


    no, it was just for illustration.... roles are full string names...
    'god' 'administrator' 'manager', 'owner', 'customer'
    Initially I thought using an additional integer field as a 'priority'
    'god' priority > 'administrator' priority > etc....

    the objective is presenting a collection for select option depending
    upon the current_user role
    if 'god' then all collection (he can CRUD any role)
    if 'admin' then all collection - 'god' and 'admin'
    ......
     
    Josselin, Aug 11, 2006
    #10
  11. Josselin

    Josselin Guest

    On 2006-08-10 22:01:38 +0200, Chad Perrin <> said:

    > On Fri, Aug 11, 2006 at 01:20:08AM +0900, Josselin wrote:
    >> I know I can write it the 'ugly common way' (loop)
    >> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >>
    >> here is an array
    >> roles = [ "a", "b", "c", "d", "e" ]

    >
    > Do the "roles" have to be those letters, or did you just use them to
    > illustrate what you're doing? If you can use numbers for "roles"
    > instead, a whole new realm of possibilities opens up using comparison
    > operators.


    yeah see my answer to Daniel... I believe adding an integer priority
    field will be easier (sure.. if I need to add new roles later...)
    thanks
     
    Josselin, Aug 11, 2006
    #11
  12. Josselin

    Josselin Guest

    On 2006-08-10 18:37:18 +0200, "Paolo Negri" <> said:

    > Some more infos about what are the relations among the User class and
    > the roles array would be nice.
    >
    > Anyway you can easily rewrite your role= method of the User class to
    > something like this
    >
    > def role=(value, array)
    > self.role = array.delete value if array.member? value
    > end
    >
    > or, if you are happy to end up with a role of nil in case the role is
    > invalid/already given away
    >
    > def role=(value, array)
    > self.role = array.delete value
    > end
    >
    >
    > On 10/08/06, Josselin <> wrote:
    >> I know I can write it the 'ugly common way' (loop)
    >> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >>
    >> here is an array
    >> roles = [ "a", "b", "c", "d", "e" ]
    >>
    >> Depending upon a variable 'user.role',
    >> I would like to suppress all elements in the array , less or equal to
    >> this variable
    >>
    >> ex :
    >> user.role = "a" #=> roles = ["b", "c", "d", "e" ]
    >> "a" deleted
    >> user.role = "b" #=> roles = ["c", "d", "e" ] "a",
    >> "b" deleted
    >> user.role = "c" #=> roles = [ "d", "e" ] "a",
    >> "b", "c" deleted
    >> user.role = "d" #=> roles = [ "e" ]
    >> "a", "b", "c", "d" deleted
    >> user.role = "e" # do nothing
    >>
    >> thanks for your tips
    >>
    >> Joss
    >> (I am on my way to buy the Ruby Recipes PDF Cookbook...)


    in this particular case, 'roles' array is built from the table 'roles',
    all values are possible roles for a new user so I don't modify the database
    this 'roles' array is presented as select options,

    'roles' array content is based on current_user.role
    if current_user.role is 'god' then all collection (he can CRUD any
    role) is presented
    if current_user.role is 'admin' then all collection minus 'god' and
    'admin' (an admin cannot create god users or admini users)....

    thanks
     
    Josselin, Aug 11, 2006
    #12
  13. On 8/11/06, Josselin <> wrote:
    > On 2006-08-10 22:01:38 +0200, Chad Perrin <> said:
    >
    > > On Fri, Aug 11, 2006 at 01:20:08AM +0900, Josselin wrote:
    > >> I know I can write it the 'ugly common way' (loop)
    > >> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    > >>
    > >> here is an array
    > >> roles = [ "a", "b", "c", "d", "e" ]

    > >
    > > Do the "roles" have to be those letters, or did you just use them to
    > > illustrate what you're doing? If you can use numbers for "roles"
    > > instead, a whole new realm of possibilities opens up using comparison
    > > operators.

    >
    > yeah see my answer to Daniel... I believe adding an integer priority
    > field will be easier (sure.. if I need to add new roles later...)
    > thanks


    You could make a Role class, define a <=> operator and mix in Comparable.

    martin
     
    Martin DeMello, Aug 11, 2006
    #13
  14. Josselin

    Josselin Guest

    On 2006-08-10 18:25:19 +0200, Philip Hallstrom <> said:

    >> I know I can write it the 'ugly common way' (loop)
    >> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >>
    >> here is an array
    >> roles = [ "a", "b", "c", "d", "e" ]
    >>
    >> Depending upon a variable 'user.role',
    >> I would like to suppress all elements in the array , less or equal to
    >> this variable
    >>
    >> ex :
    >> user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a" deleted
    >> user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b" deleted
    >> user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c" deleted
    >> user.role = "d" #=> roles = [ "e" ] "a", "b", "c", "d" deleted
    >> user.role = "e" # do nothing

    >
    > Maybe...
    >
    > roles = roles.map {|x| x <= user.role ? x : nil }.compact
    >
    > haven't tested it though...


    I'll test it, values in array are strings : 'god', 'administrator',
    ''manager', 'owner', 'customer'
    exclusion is based on a prority order
    if current_user role is 'god' then exclude 'god' (there can be only one god)
    if current_user role is 'administrator' then exclude 'god' and 'administrator'
    if current_user role is 'manager' then exclude 'god' and
    'administrator' and 'manager'
    if current_user role is 'owner' then exclude 'god' and 'administrator'
    and 'manager' and 'owner'
    ....
    as roles could change in the future (and also ro avoid possible
    localization issues) I believe it would be better to work with an
    additional integer priority field in the 'role' table, so I can sort
    the collection on priority and get a sorted roles array whatever is in
    the table...
    thanks
     
    Josselin, Aug 11, 2006
    #14
  15. Josselin

    Josselin Guest

    On 2006-08-10 18:22:50 +0200, Robert Klemme <> said:

    > On 10.08.2006 18:17, Josselin wrote:
    >> I know I can write it the 'ugly common way' (loop)
    >> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >>
    >> here is an array
    >> roles = [ "a", "b", "c", "d", "e" ]
    >>
    >> Depending upon a variable 'user.role',
    >> I would like to suppress all elements in the array , less or equal to
    >> this variable
    >>
    >> ex :
    >> user.role = "a" #=> roles = ["b", "c", "d", "e" ] "a" deleted
    >> user.role = "b" #=> roles = ["c", "d", "e" ] "a", "b" deleted
    >> user.role = "c" #=> roles = [ "d", "e" ] "a", "b", "c" deleted
    >> user.role = "d" #=> roles = [ "e" ] "a", "b",
    >> "c", "d" deleted
    >> user.role = "e" # do nothing
    >>
    >> thanks for your tips
    >>
    >> Joss
    >> (I am on my way to buy the Ruby Recipes PDF Cookbook...)
    >>

    >
    > Do you actually want to modify the array or do you just want to work
    > with the reduced set? Does this help?
    >
    > >> roles = %w{a b c d e f}

    > => ["a", "b", "c", "d", "e", "f"]
    > >> roles.select {|r| r >= "c"}

    > => ["c", "d", "e", "f"]
    > >> roles.select {|r| r > "c"}

    > => ["d", "e", "f"]
    > >> roles

    > => ["a", "b", "c", "d", "e", "f"]
    > >> roles.delete_if {|r| r <= "c"}

    > => ["d", "e", "f"]
    > >> roles

    > => ["d", "e", "f"]
    >
    > Kind regards
    >
    > robert


    thanks I'll look over it .. I'll check how it works with string values
     
    Josselin, Aug 11, 2006
    #15
  16. Josselin wrote:
    > <snip>
    > I'll test it, values in array are strings : 'god', 'administrator',
    > ''manager', 'owner', 'customer'
    > exclusion is based on a prority order
    > if current_user role is 'god' then exclude 'god' (there can be only
    > one god)


    It's a monotheistic system then? ;)

    -Justin
     
    Justin Collins, Aug 11, 2006
    #16
  17. Josselin

    Guest

    Hi --

    On Sat, 12 Aug 2006, Justin Collins wrote:

    > Josselin wrote:
    >> <snip>
    >> I'll test it, values in array are strings : 'god', 'administrator',
    >> ''manager', 'owner', 'customer'
    >> exclusion is based on a prority order
    >> if current_user role is 'god' then exclude 'god' (there can be only one
    >> god)

    >
    > It's a monotheistic system then? ;)


    But the customer is always right :)


    David

    --
    http://www.rubypowerandlight.com => Ruby/Rails training & consultancy
    ----> SEE SPECIAL DEAL FOR RUBY/RAILS USERS GROUPS! <-----
    http://dablog.rubypal.com => D[avid ]A[. ]B[lack's][ Web]log
    http://www.manning.com/black => book, Ruby for Rails
    http://www.rubycentral.org => Ruby Central, Inc.
     
    , Aug 11, 2006
    #17
  18. Josselin

    Josselin Guest

    On 2006-08-11 08:39:25 +0200, "Martin DeMello" <> said:

    > On 8/11/06, Josselin <> wrote:
    >> On 2006-08-10 22:01:38 +0200, Chad Perrin <> said:
    >>
    >> > On Fri, Aug 11, 2006 at 01:20:08AM +0900, Josselin wrote:
    >> >> I know I can write it the 'ugly common way' (loop)
    >> >> but I'd like to see how it can be done the Ruby way ... (I am a newbie...)
    >> >>
    >> >> here is an array
    >> >> roles = [ "a", "b", "c", "d", "e" ]
    >> >
    >> > Do the "roles" have to be those letters, or did you just use them to
    >> > illustrate what you're doing? If you can use numbers for "roles"
    >> > instead, a whole new realm of possibilities opens up using comparison
    >> > operators.

    >>
    >> yeah see my answer to Daniel... I believe adding an integer priority
    >> field will be easier (sure.. if I need to add new roles later...)
    >> thanks

    >
    > You could make a Role class, define a <=> operator and mix in Comparable.
    >
    > martin


    thanks Martin, that's what I finally did... writing my own Role class
    (the original one was part of an authorization plugin... did not have
    some much control over it )

    joss
     
    Josselin, Aug 12, 2006
    #18
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. HNguyen
    Replies:
    4
    Views:
    2,452
    HNguyen
    Dec 21, 2004
  2. M
    Replies:
    3
    Views:
    417
    Roedy Green
    Jun 2, 2004
  3. Love Rhino
    Replies:
    28
    Views:
    1,510
    Mike Schilling
    Sep 25, 2004
  4. Nemisis
    Replies:
    2
    Views:
    741
    senfo
    Feb 28, 2007
  5. vasudevram
    Replies:
    0
    Views:
    252
    vasudevram
    Apr 15, 2007
Loading...

Share This Page