ruby-changes:48303
From: nobu <ko1@a...>
Date: Wed, 25 Oct 2017 14:44:45 +0900 (JST)
Subject: [ruby-changes:48303] nobu:r60417 (trunk): io.c: write a newline together
nobu 2017-10-25 14:44:38 +0900 (Wed, 25 Oct 2017) New Revision: 60417 https://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=revision&revision=60417 Log: io.c: write a newline together * io.c (rb_io_puts): write a newline together at once for each argument. based on the patch by rohitpaulk (Rohit Kuruvilla) at [ruby-core:83508]. [Feature #14042] Modified files: trunk/io.c trunk/spec/ruby/core/io/puts_spec.rb trunk/test/ruby/test_io.rb Index: test/ruby/test_io.rb =================================================================== --- test/ruby/test_io.rb (revision 60416) +++ test/ruby/test_io.rb (revision 60417) @@ -2445,6 +2445,19 @@ End https://github.com/ruby/ruby/blob/trunk/test/ruby/test_io.rb#L2445 end) end + def test_puts_parallel + pipe(proc do |w| + threads = [] + 100.times do + threads << Thread.new { w.puts "hey" } + end + threads.each(&:join) + w.close + end, proc do |r| + assert_equal("hey\n" * 100, r.read) + end) + end + def test_display pipe(proc do |w| "foo".display(w) Index: io.c =================================================================== --- io.c (revision 60416) +++ io.c (revision 60417) @@ -1686,6 +1686,16 @@ rb_io_write(VALUE io, VALUE str) https://github.com/ruby/ruby/blob/trunk/io.c#L1686 return rb_funcallv(io, id_write, 1, &str); } +static VALUE +rb_io_writev(VALUE io, int argc, VALUE *argv) +{ + if (argc > 1 && rb_obj_method_arity(io, id_write) == 1) { + do rb_io_write(io, *argv++); while (--argc); + return argv[0]; /* unused right now */ + } + return rb_funcallv(io, id_write, argc, argv); +} + /* * call-seq: * ios << obj -> ios @@ -7572,8 +7582,8 @@ io_puts_ary(VALUE ary, VALUE out, int re https://github.com/ruby/ruby/blob/trunk/io.c#L7582 VALUE rb_io_puts(int argc, const VALUE *argv, VALUE out) { - int i; - VALUE line; + int i, n; + VALUE line, args[2]; /* if no argument given, print newline. */ if (argc == 0) { @@ -7590,11 +7600,13 @@ rb_io_puts(int argc, const VALUE *argv, https://github.com/ruby/ruby/blob/trunk/io.c#L7600 } line = rb_obj_as_string(argv[i]); string: - rb_io_write(out, line); + n = 0; + args[n++] = line; if (RSTRING_LEN(line) == 0 || !rb_str_end_with_asciichar(line, '\n')) { - rb_io_write(out, rb_default_rs); + args[n++] = rb_default_rs; } + rb_io_writev(out, n, args); } return Qnil; Index: spec/ruby/core/io/puts_spec.rb =================================================================== --- spec/ruby/core/io/puts_spec.rb (revision 60416) +++ spec/ruby/core/io/puts_spec.rb (revision 60417) @@ -43,18 +43,16 @@ describe "IO#puts" do https://github.com/ruby/ruby/blob/trunk/spec/ruby/core/io/puts_spec.rb#L43 object.should_receive(:method_missing).with(:to_ary) object.should_receive(:to_s).and_return("#<Object:0x...>") - @io.should_receive(:write).with("#<Object:0x...>") - @io.should_receive(:write).with("\n") @io.puts(object).should == nil + ScratchPad.recorded.should == "#<Object:0x...>\n" end it "calls :to_ary before writing non-string objects" do object = mock('hola') object.should_receive(:to_ary).and_return(["hola"]) - @io.should_receive(:write).with("hola") - @io.should_receive(:write).with("\n") @io.puts(object).should == nil + ScratchPad.recorded.should == "hola\n" end it "calls :to_s before writing non-string objects that don't respond to :to_ary" do @@ -69,9 +67,8 @@ describe "IO#puts" do https://github.com/ruby/ruby/blob/trunk/spec/ruby/core/io/puts_spec.rb#L67 object = mock('hola') object.should_receive(:to_s).and_return(false) - @io.should_receive(:write).with(object.inspect.split(" ")[0] + ">") - @io.should_receive(:write).with("\n") @io.puts(object).should == nil + ScratchPad.recorded.should == object.inspect.split(" ")[0] + ">\n" end it "writes each arg if given several" do -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/