diff options
author | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-07-20 08:39:12 +0000 |
---|---|---|
committer | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-07-20 08:39:12 +0000 |
commit | 42c6a5137e46b885ab28b267f85c0ddc8d49b195 (patch) | |
tree | 507dc795b1f2a1420947e6b6be193ad0bbd6c496 /enum.c | |
parent | f14d64638a461ff660d16b42ae827b46a0cec91b (diff) |
enum.c: Enumerable#uniq
* enum.c (enum_uniq): new method Enumerable#uniq.
[Feature #11090]
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@55709 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'enum.c')
-rw-r--r-- | enum.c | 35 |
1 files changed, 35 insertions, 0 deletions
@@ -3793,6 +3793,40 @@ enum_sum(int argc, VALUE* argv, VALUE obj) } } +static VALUE +uniq_func(RB_BLOCK_CALL_FUNC_ARGLIST(i, hash)) +{ + rb_hash_add_new_element(hash, i, i); + return Qnil; +} + +static VALUE +uniq_iter(RB_BLOCK_CALL_FUNC_ARGLIST(i, hash)) +{ + rb_hash_add_new_element(hash, rb_yield_values2(argc, argv), i); + return Qnil; +} + +/* + * call-seq: + * enum.uniq -> new_ary + * enum.uniq { |item| ... } -> new_ary + */ + +static VALUE +enum_uniq(VALUE obj) +{ + VALUE hash, ret; + rb_block_call_func *const func = + rb_block_given_p() ? uniq_iter : uniq_func; + + hash = rb_obj_hide(rb_hash_new()); + rb_block_call(obj, id_each, 0, 0, func, hash); + ret = rb_hash_values(hash); + rb_hash_clear(hash); + return ret; +} + /* * The <code>Enumerable</code> mixin provides collection classes with * several traversal and searching methods, and with the ability to @@ -3866,6 +3900,7 @@ Init_Enumerable(void) rb_define_method(rb_mEnumerable, "slice_when", enum_slice_when, 0); rb_define_method(rb_mEnumerable, "chunk_while", enum_chunk_while, 0); rb_define_method(rb_mEnumerable, "sum", enum_sum, -1); + rb_define_method(rb_mEnumerable, "uniq", enum_uniq, 0); id_next = rb_intern("next"); id_call = rb_intern("call"); |