example ruby activerecord hash

ruby grape example



hash[''key''] a hash.key en Ruby (5)

En lugar de copiar todas las cosas del hash, puede agregar algo de comportamiento a Hash para realizar búsquedas.

Si agrega esta definición, extienda Hash para manejar todos los métodos desconocidos como búsquedas de hash:

class Hash def method_missing(n) self[n.to_s] end end

Ten en cuenta que esto significa que nunca verás errores si llamas al método incorrecto en hash; obtendrás lo que devuelva la búsqueda hash correspondiente.

Puede reducir enormemente los problemas de depuración que esto puede causar al poner el método solo en un hash específico o tantos hashes como necesite:

a={''foo''=>5, ''goo''=>6} def a.method_missing(n) self[n.to_s] end

La otra observación es que cuando el sistema llama a method_missing , le da un argumento de Symbol . Mi código lo convirtió en una String . Si sus claves hash no son cadenas, este código nunca devolverá esos valores; si n.to_s por símbolos en lugar de cadenas, simplemente sustituya n por n.to_s arriba.

Tengo aa hash

foo = {''bar''=>''baz''}

Me gustaría llamar a foo.bar #=> ''baz''

Mi motivación es reescribir una consulta activerecord en una consulta sql en bruto (usando el modelo # find_by_sql). Esto devuelve un hash con los valores de la cláusula SELECT como claves. Sin embargo, mi código existente se basa en la notación de puntos object.method. Me gustaría hacer una mínima reescritura de código. Gracias.

Editar: parece que Lua tiene esta característica:

point = { x = 10, y = 20 } -- Create new table print(point["x"]) -- Prints 10 print(point.x) -- Has exactly the same meaning as line above


Hay algunas gemas para esto. Allí está mi gema reciente, hash_dot y algunas gemas con nombres similares que descubrí cuando dot_hash el mío en RubyGems, incluido dot_hash .

HashDot permite la sintaxis de notación de puntos, al mismo tiempo que responde a las preocupaciones sobre NoMethodErrors abordadas por @avdi. Es más rápido y más transitable que un objeto creado con OpenStruct.

require ''hash_dot'' a = {b: {c: {d: 1}}}.to_dot a.b.c.d => 1 require ''open_struct'' os = OpenStruct.new(a) os.b => {c: {d: 1}} os.b.c.d => NoMethodError

También mantiene el comportamiento esperado cuando se llaman no métodos.

a.non_method => NoMethodError

Por favor, siéntase libre de enviar mejoras o errores a HashDot.


Lo que estás buscando se llama OpenStruct . Es parte de la biblioteca estándar.


Una buena solución:

class Hash def method_missing(method, *opts) m = method.to_s if self.has_key?(m) return self[m] elsif self.has_key?(m.to_sym) return self[m.to_sym] end super end end

Nota: esta implementación solo tiene un error conocido:

x = { ''test'' => ''aValue'', :test => ''bar''} x.test # => ''aValue''

Si prefiere búsquedas de símbolos en lugar de búsquedas de cadenas, cambie las dos condiciones ''si''


>> require ''ostruct'' => [] >> foo = {''bar''=>''baz''} => {"bar"=>"baz"} >> foo_obj = OpenStruct.new foo => #<OpenStruct bar="baz"> >> foo_obj.bar => "baz" >>