diff options
author | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-07-11 07:00:58 +0000 |
---|---|---|
committer | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2016-07-11 07:00:58 +0000 |
commit | e96f0f76b33bc680210cbe67f4ece560bae9ab03 (patch) | |
tree | 06487bacc8f7c79627ceedf2976f9d278e2690c1 | |
parent | a00ec4cf3a43b67c8a3166ae22d321089446cf98 (diff) | |
download | ruby-e96f0f76b33bc680210cbe67f4ece560bae9ab03.tar.gz |
stringio.c: convert arguments just once
* ext/stringio/stringio.c (strio_each, strio_readlines): convert
arguments just once before reading, instead of conversions for
each lines, as r55603.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@55629 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r-- | ChangeLog | 6 | ||||
-rw-r--r-- | ext/stringio/stringio.c | 44 |
2 files changed, 38 insertions, 12 deletions
@@ -1,3 +1,9 @@ +Mon Jul 11 16:00:56 2016 Nobuyoshi Nakada <nobu@ruby-lang.org> + + * ext/stringio/stringio.c (strio_each, strio_readlines): convert + arguments just once before reading, instead of conversions for + each lines, as r55603. + Sun Jul 10 19:53:41 2016 Martin Duerst <duerst@it.aoyama.ac.jp> * enc/iso_8859_10.c, test/ruby/enc/test_case_comprehensive.rb: diff --git a/ext/stringio/stringio.c b/ext/stringio/stringio.c index f35c702d0a..a5a2327366 100644 --- a/ext/stringio/stringio.c +++ b/ext/stringio/stringio.c @@ -982,12 +982,16 @@ bm_search(const char *little, long llen, const char *big, long blen, const long return -1; } -static VALUE -strio_getline(int argc, VALUE *argv, struct StringIO *ptr) +struct getline_arg { + VALUE rs; + long limit; +}; + +static struct getline_arg * +prepare_getline_args(struct getline_arg *arg, int argc, VALUE *argv) { - const char *s, *e, *p; - long n, limit = 0; VALUE str, lim; + long limit = -1; rb_scan_args(argc, argv, "02", &str, &lim); switch (argc) { @@ -1000,7 +1004,6 @@ strio_getline(int argc, VALUE *argv, struct StringIO *ptr) VALUE tmp = rb_check_string_type(str); if (NIL_P(tmp)) { limit = NUM2LONG(str); - if (limit == 0) return rb_str_new(0,0); str = rb_rs; } else { @@ -1014,6 +1017,17 @@ strio_getline(int argc, VALUE *argv, struct StringIO *ptr) if (!NIL_P(lim)) limit = NUM2LONG(lim); break; } + arg->rs = str; + arg->limit = limit; + return arg; +} + +static VALUE +strio_getline(struct getline_arg *arg, struct StringIO *ptr) +{ + const char *s, *e, *p; + long n, limit = arg->limit; + VALUE str = arg->rs; if (ptr->pos >= (n = RSTRING_LEN(ptr->string))) { return Qnil; @@ -1086,8 +1100,14 @@ strio_getline(int argc, VALUE *argv, struct StringIO *ptr) static VALUE strio_gets(int argc, VALUE *argv, VALUE self) { - VALUE str = strio_getline(argc, argv, readable(self)); + struct getline_arg arg; + VALUE str; + + if (prepare_getline_args(&arg, argc, argv)->limit == 0) { + return rb_str_new(0, 0); + } + str = strio_getline(&arg, readable(self)); rb_lastline_set(str); return str; } @@ -1126,16 +1146,16 @@ static VALUE strio_each(int argc, VALUE *argv, VALUE self) { VALUE line; + struct getline_arg arg; StringIO(self); RETURN_ENUMERATOR(self, argc, argv); - if (argc > 0 && !NIL_P(argv[argc-1]) && NIL_P(rb_check_string_type(argv[argc-1])) && - NUM2LONG(argv[argc-1]) == 0) { + if (prepare_getline_args(&arg, argc, argv)->limit == 0) { rb_raise(rb_eArgError, "invalid limit: 0 for each_line"); } - while (!NIL_P(line = strio_getline(argc, argv, readable(self)))) { + while (!NIL_P(line = strio_getline(&arg, readable(self)))) { rb_yield(line); } return self; @@ -1165,15 +1185,15 @@ static VALUE strio_readlines(int argc, VALUE *argv, VALUE self) { VALUE ary, line; + struct getline_arg arg; StringIO(self); ary = rb_ary_new(); - if (argc > 0 && !NIL_P(argv[argc-1]) && NIL_P(rb_check_string_type(argv[argc-1])) && - NUM2LONG(argv[argc-1]) == 0) { + if (prepare_getline_args(&arg, argc, argv)->limit == 0) { rb_raise(rb_eArgError, "invalid limit: 0 for readlines"); } - while (!NIL_P(line = strio_getline(argc, argv, readable(self)))) { + while (!NIL_P(line = strio_getline(&arg, readable(self)))) { rb_ary_push(ary, line); } return ary; |