Julian solution is more elegant. I like it. It has a functional
difference in that it catches partial names--for instance tim would
match to timothy (probably good in this case)--but rand would match
crand.

That being the case searching tim matches [1], but tim rand matches
[1,3]. More information leads to less specificity. when a perfect
match is available, that should be the only item returned--i would
think.



On May 27, 3:48 am, Julian Leviston <[email protected]> wrote:
> Sorry, but that code below is really unidiomatic ruby.
>
> Given the following:
>
> >> given a data structure like @contacts =
> >> [{:first_name=>'tim', :last_name=>'rand', :id =
> >> 1},{:first_name=>'jim', :last_name=>'band', :id =>
> >> 2},{:first_name=>'him', :last_name=>'crand', :id => 3}]
> >> and given a query may be first, last, or both names
> >> return id number for matches
>
> @contacts = [{:first_name=>'tim', :last_name=>'rand', :id => 1},
> {:first_name=>'jim', :last_name=>'band', :id =>2},
> {:first_name=>'him', :last_name=>'crand', :id => 3}]
>
> keywords = "ran"
> @contacts.select{|hash| keywords.split.any?{|keyword|  
> hash.values.join.include?(keyword)}}.map{|hash| hash[:id]}
>
> # or more prettily:
>
> @contacts.select do |hash|
>         keywords.split.any? do |keyword|
>                 hash.values.join.include?(keyword)
>         end
> end. # note the period at the end of this line... indicating we still  
> want to send the result of this select method another message yet...  
> (ie the map message below).
> map do |hash|
>         hash[:id]
> end
>
> => [1, 3]
>
> if you really need to make a method of it (tho I don't know why you  
> would), you can do so thusly:
>
> class ArrayOfHashes < Array
>         def search_array_with_hashes(keywords)
>                 found_hashes = self.select{|hash| 
> keywords.split.any?{|keyword|  
> hash.values.join.include?(keyword)}}
>                 found_hashes.map{|hash| hash[:id]}
>         end
> end
>
> @contacts = ArrayOfHashes.new(@contacts)
>
> @contacts.search_array_with_hashes("ran")
> => [1, 3]
> @contacts.search_array_with_hashes("band")
> => [2]
> @contacts.search_array_with_hashes("tim rand")
> => [1, 3]
> @contacts.search_array_with_hashes("crand")
> => [3]
> @contacts.search_array_with_hashes("jam")
> => []
>
> >> p search_array_with_hashes(parse_query("band"))
> >> p search_array_with_hashes(parse_query("tim rand"))
> >> p search_array_with_hashes(parse_query("crand"))
>
> ----------------------------------------------
> Learn:http://sensei.zenunit.com/
> Last updated 20-May-09 (Rails, Basic Unix)
> Blog:http://random8.zenunit.com/
> Twitter:http://twitter.com/random8r
>
> On 26/05/2009, at 7:07 PM, Robert Scott wrote:
>
>
>
>
>
> > Tim,
>
> > Thanks again for the detailed thoughts. It looks like your approach is
> > structured in a way that should handle what I'm looking for, and  
> > provide
> > a framework for future expansion. I went ahead and implemented it in,
> > and am trying to resolve an issue now (NoMethodError (undefined method
> > `values_at') for `search_array_with_hashes' but I'll let you know once
> > it gets working.
>
> > Cheers!
>
> > timr wrote:
> >> Hi again Robert,
> >> There might be methods build into rails for doing this, but when you
> >> have a very specific case, you might just roll out your own methods  
> >> to
> >> get exactly what you want:
>
> >> =begin
> >> given a data structure like @contacts =
> >> [{:first_name=>'tim', :last_name=>'rand', :id =
> >> 1},{:first_name=>'jim', :last_name=>'band', :id =>
> >> 2},{:first_name=>'him', :last_name=>'crand', :id => 3}]
> >> and given a query may be first, last, or both names
> >> return id number for matches
> >> =end
>
> >> #here is our search array
> >> @contacts = [{:first_name=>'tim', :last_name=>'rand', :id =>
> >> 1},{:first_name=>'jim', :last_name=>'band', :id =>
> >> 2},{:first_name=>'him', :last_name=>'crand', :id => 3},
> >> {:first_name=>'shim', :last_name=>'crand', :id => 4}]
>
> >> #method to separate names if more than one is given
> >> def parse_query(query)
> >>  if query.match(" ")
> >>    name1, name2 = query.split(/ /)
> >>  else
> >>    name1 = query
> >>    return name1.to_a
> >>  end
> >>  return [name1, name2]
> >> end
>
> >> #find any name in hash field and return the ids
> >> def search_array_with_hashes(array_with_name_or_names)
> >> �...@hits = []
> >>  #search first names
> >>  array_with_name_or_names.each do |name|
> >> �[email protected] do |hash|
> >>   �...@hits << hash[:id] if hash.values.include?(name)
> >>  end
> >>  end
> >> �[email protected]
> >> end
>
> >> #usage/test case examples
> >> p search_array_with_hashes(parse_query("band"))
> >> p search_array_with_hashes(parse_query("tim rand"))
> >> p search_array_with_hashes(parse_query("crand"))
> >> # >> [2]
> >> # >> [1]
> >> # >> [3, 4]
>
> >> Will that do the trick?
> >> Tim
>
> >> On May 25, 1:23 am, Robert Scott <[email protected]>
>
> > --
> > Posted viahttp://www.ruby-forum.com/.- Hide quoted text -
>
> - Show quoted text -
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups "Ruby 
on Rails: Talk" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to 
[email protected]
For more options, visit this group at 
http://groups.google.com/group/rubyonrails-talk?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to