ext/template/google_hash.cpp.erb in google_hash-0.2.1 vs ext/template/google_hash.cpp.erb in google_hash-0.3.0

- old
+ new

@@ -13,24 +13,40 @@ using __gnu_cxx::hash; // or __gnu_cxx::hash, or maybe tr1::hash, depending on your OS extern "C" { // some helpers +<% + # not yet used... + if false +%> struct eqstr { bool operator()(const char* s1, const char* s2) const { return (s1 == s2) || (s1 && s2 && strcmp(s1, s2) == 0); } }; -static hash<const char*> H; +struct eqint +{ + inline bool operator()(int s1, int s2) const + { + return s1 == s2; + } +}; -// hashing it is like hash<const char*> +<% end %> + static ID id_eql, id_hash; +<% if key_type == 'VALUE' %> +static hash<const char*> H; + +// hashing it is like hash<const char*> + struct eqrb { bool operator()(const VALUE s1, const VALUE s2) const { // speeds up populate int 18/11 @@ -45,10 +61,14 @@ return RTEST(rb_funcall(s1, id_eql, 1, s2)); } }; +#ifndef RBIGNUM_DIGITS +# define RBIGNUM_DIGITS(a) RBIGNUM(a)->digits +#endif + struct hashrb { size_t operator()(VALUE hash_me) const { // stolen from hash.c populate -> 0.64 0.625 @@ -66,18 +86,17 @@ case T_FIXNUM: case T_FLOAT: case T_SYMBOL: // ltodo return hash_me; - <% unless RUBY_VERSION < '1.9' %> case T_BIGNUM: - return LONG2FIX(((long*)(RBIGNUM_DIGITS(hash_me)))[0]); // its first digit...I'm thinkin' - <% end %> - case T_STRING: + return LONG2FIX(((long*)(RBIGNUM_DIGITS(hash_me)))[0]); // its first digit...I'm thinkin' + // not sure if this is faster or not... + //case T_STRING: //return H(StringValueCStr(hash_me)); // populate/lookup 0.26 -> 0.23 [core is 0.16 somehow] // perhaps they cache? - return H(RSTRING_PTR(hash_me)); // 0.23 -> -.22 + //return H(RSTRING_PTR(hash_me)); // 0.23 -> -.22 } VALUE hval = rb_funcall(hash_me, id_hash, 0); retry: @@ -95,20 +114,13 @@ } } }; +<% end %> - /* we end up not needing this...or at least not using it, I don't know if it would be faster than using the default or not -struct eqint -{ - inline bool operator()(int s1, int s2) const - { - return s1 == s2; - } -}; */ typedef struct { <%= type %>_hash_map< <%= key_type %>, <%= value_type %> <%= extra_hash_params %> > *hash_map; @@ -166,22 +178,30 @@ static VALUE rb_ghash_set(VALUE cb, VALUE set_this, VALUE to_this) { <% if assert_key_type %> if(!(TYPE(set_this) == <%= assert_key_type %>)) { - rb_raise(rb_eTypeError, "not valid value #{assert_key_type}"); + rb_raise(rb_eTypeError, "not valid key #{assert_key_type}"); } <% end %> + + <% if assert_value_type %> + if(!(TYPE(to_this) == <%= assert_value_type %>)) { + rb_raise(rb_eTypeError, "not valid value #{assert_value_type}"); + } + <% end %> + + RCallback* cbs = GetCallbackStruct(cb); (*cbs->hash_map)[ <%= convert_keys_from_ruby %>(set_this)] = <%= convert_values_from_ruby %>(to_this); return to_this; // ltodo test that it returns value... } static VALUE rb_ghash_get(VALUE cb, VALUE get_this) { // TODO optionally not assert [?] <% if assert_key_type %> if(!(TYPE(get_this) == <%= assert_key_type %>)) { - rb_raise(rb_eTypeError, "not valid value #{assert_key_type}"); + rb_raise(rb_eTypeError, "not valid key #{assert_key_type}"); } <% end %> RCallback* cbs = GetCallbackStruct(cb); <%= type %>_hash_map< <%= key_type %>, <%= value_type %> <%= extra_hash_params %> >::iterator out = cbs->hash_map->find(<%= convert_keys_from_ruby %>(get_this));