[#34011] Should --verbose be equal to -v ? — Yugui <yugui@...>

Yuguiです。

15 messages 2008/03/10
[#34012] Re: Should --verbose be equal to -v ? — Yukihiro Matsumoto <matz@...> 2008/03/10

まつもと ゆきひろです

[#34105] rational.rb, complex.rb and mathn.rb — Tadayoshi Funaba <tadf@...>

rational と complex が組み込みになったことで、lib/mathn.rb の意義は薄

29 messages 2008/03/22
[#34106] Re: rational.rb, complex.rb and mathn.rb — Tadayoshi Funaba <tadf@...> 2008/03/22

現時点で rational.rb と complex.rb を残しているのは、それが無難だから

[#34107] Re: rational.rb, complex.rb and mathn.rb — Tadayoshi Funaba <tadf@...> 2008/03/22

で、かなり選択肢を絞った叩き台です。

[#34120] Re: rational.rb, complex.rb and mathn.rb — keiju@... (石塚圭樹) 2008/03/24

けいじゅ@いしつかです.

[#34125] Re: rational.rb, complex.rb and mathn.rb — Shin-ichiro HARA <sinara@...> 2008/03/25

原です。

[#34130] Re: rational.rb, complex.rb and mathn.rb — Tadayoshi Funaba <tadf@...> 2008/03/25

> 私も Complex の組み込みは Rational とは比較にならないくらい、仕様が決め

[#34158] Complex組み込み — Masahiro TANAKA <masa16.tanaka@...>

Complexが組み込みになるそうですが、これはcomplex.rbを踏襲して、

49 messages 2008/03/27
[#34161] Re: Complex組み込み — Shin-ichiro HARA <sinara@...> 2008/03/28

原です。

[#34168] Re: Complex組み込み — Tadayoshi Funaba <tadf@...> 2008/03/28

> 今までの Complex は、complex.rb にほぼ残して、たとえば Rational 成分

[#34186] Re: Complex組み込み — Shin-ichiro HARA <sinara@...> 2008/03/31

原です。

[#34187] Re: Complex組み込み — Tadayoshi Funaba <tadf@...> 2008/03/31

> そうです。Complex が難しい、という話を書いておくと、

[#34193] Re: Complex組み込み — Yukihiro Matsumoto <matz@...> 2008/03/31

まつもと ゆきひろです

[#34203] Re: Complex組み込み — Tadayoshi Funaba <tadf@...> 2008/04/01

> |僕としては、/ 演算子の振舞いについて前向きに検討してほしいです。

[#34215] Re: Complex組み込み — Yukihiro Matsumoto <matz@...> 2008/04/02

まつもと ゆきひろです

[#34166] Re: Complex組み込み — Tadayoshi Funaba <tadf@...> 2008/03/28

> となるようですが、別の実装として、

[ruby-dev:33969] ungetc and encoding (Re: Re: --encoding affects script encoding)

From: Nobuyoshi Nakada <nobu@...>
Date: 2008-03-03 06:56:33 UTC
List: ruby-dev #33969
なかだです。

At Mon, 3 Mar 2008 00:54:33 +0900,
Tanaka Akira wrote in [ruby-dev:33960]:
> > コミットしましたが、IO#ungetcでのエンコーディングの扱いが抜けて
> > いることに気づきました。
> 
> >      else {
> >  	SafeStringValue(c);
> > +	enc = io_input_encoding(fptr);
> > +    }
> > +    if (enc && enc != rb_enc_get(c)) {
> > +	c = rb_funcall(c, id_encode, 1, rb_enc_from_encoding(enc));
> >      }
> >      io_ungetc(c, fptr);
> 
> encdetect を実装するには、IO からバイト列で読み出したものを
> バイト列として ungetc することが必要なんですが、それはできる
> でしょうか。

それは現状でもできないですね。?xもStringになったことでもあるし、
0..255の整数の並びはバイト列として戻す、というのでもいいかも。

> 別メソッドかなぁ?

getcとgetbyteも分けたことを考えれば、こっちですかねぇ。
ungetbyteというのはいまいちな気がしますが。


Index: io.c
===================================================================
--- io.c	(revision 15671)
+++ io.c	(working copy)
@@ -312,9 +312,7 @@ io_unread(rb_io_t *fptr)
 }
 
-static void
-io_ungetc(VALUE str, rb_io_t *fptr)
+static char *
+io_unget_space(long len, rb_io_t *fptr)
 {
-    int len = RSTRING_LEN(str);
-
     if (fptr->rbuf == NULL) {
         fptr->rbuf_off = 0;
@@ -337,5 +335,11 @@ io_ungetc(VALUE str, rb_io_t *fptr)
     fptr->rbuf_off-=len;
     fptr->rbuf_len+=len;
-    MEMMOVE(fptr->rbuf+fptr->rbuf_off, RSTRING_PTR(str), char, len);
+    return fptr->rbuf+fptr->rbuf_off;
+}
+
+static void
+io_ungetc(const char *ptr, long len, rb_io_t *fptr)
+{
+    MEMMOVE(io_unget_space(len, fptr), ptr, char, len);
 }
 
@@ -680,10 +684,10 @@ io_fwrite(VALUE str, rb_io_t *fptr)
 	/* Can't use encode! because puts writes a frozen newline */
 	if (fptr->enc2) {
-	    str = rb_funcall(str, id_encode, 2, 
+	    str = rb_funcall(str, id_encode, 2,
 			     rb_enc_from_encoding(fptr->enc2),
 			     rb_enc_from_encoding(fptr->enc));
 	}
 	else {
-	    str = rb_funcall(str, id_encode, 1, 
+	    str = rb_funcall(str, id_encode, 1,
 			     rb_enc_from_encoding(fptr->enc));
 	}
@@ -1348,5 +1352,5 @@ io_enc_str(VALUE str, rb_io_t *fptr)
 	/* two encodings, so transcode from enc2 to enc */
 	/* the methods in transcode.c are static, so call indirectly */
-	str = rb_funcall(str, id_encode, 2, 
+	str = rb_funcall(str, id_encode, 2,
 			 rb_enc_from_encoding(fptr->enc),
 			 rb_enc_from_encoding(fptr->enc2));
@@ -1896,5 +1900,5 @@ prepare_getline_args(int argc, VALUE *ar
 	if (fptr->enc2) {
             VALUE rs2;
-	    rs2 = rb_funcall(rs, id_encode, 2, 
+	    rs2 = rb_funcall(rs, id_encode, 2,
 			    rb_enc_from_encoding(fptr->enc2),
 			    rb_enc_from_encoding(fptr->enc));
@@ -2414,10 +2418,11 @@ rb_io_readbyte(VALUE io)
  *  call-seq:
  *     ios.ungetc(string)   => nil
+ *     ios.ungetc(byte)     => nil
+ *     ios.ungetc(byte_ary) => nil
  *
- *  Pushes back one character (passed as a parameter) onto <em>ios</em>,
- *  such that a subsequent buffered read will return it. Only one character
- *  may be pushed back before a subsequent read operation (that is,
- *  you will be able to read only the last of several characters that have been pushed
- *  back). Has no effect with unbuffered reads (such as <code>IO#sysread</code>).
+ *  Pushes back character string or byte sequence (passed as a
+ *  parameter) onto <em>ios</em>, such that a subsequent buffered read
+ *  will return it.  Has no effect with unbuffered reads (such as
+ *  <code>IO#sysread</code>).
  *
  *     f = File.new("testfile")   #=> #<File:testfile>
@@ -2425,25 +2430,89 @@ rb_io_readbyte(VALUE io)
  *     f.ungetc(c)                #=> nil
  *     f.getc                     #=> "8"
+ *     f.ungetc(0x39, 10)         #=> nil
+ *     f.gets                     #=> "9\n"
  */
 
 VALUE
-rb_io_ungetc(VALUE io, VALUE c)
+rb_io_unget(int argc, VALUE *argv, VALUE io)
 {
     rb_io_t *fptr;
+    VALUE c;
 
     GetOpenFile(io, fptr);
     rb_io_check_readable(fptr);
+    if (argc < 1) return Qnil;
+    if (argc > 1) {		/* expects byte array */
+	/* use temporary buffer to get rid of race condition */
+	volatile VALUE str = rb_str_tmp_new(argc);
+	char *ptr = RSTRING_PTR(str);
+	int i;
+
+	for (i = 0; i < argc; ++i) {
+	    c = argv[i];
+	    ptr[i] = (char)NUM2INT(c);
+	}
+	io_ungetc(ptr, argc, fptr);
+	rb_str_resize(str, 0);
+	return Qnil;
+    }
+    c = argv[0];
     if (NIL_P(c)) return Qnil;
     if (FIXNUM_P(c)) {
-	int cc = FIX2INT(c);
-	rb_encoding *enc = io_read_encoding(fptr);
-	char buf[16];
+	char cc = (char)FIX2INT(c);
 
-	c = rb_str_new(buf, rb_enc_mbcput(cc, buf, enc));
+	io_ungetc(&cc, 1, fptr);
     }
     else {
+	rb_encoding *enc = io_input_encoding(fptr);
 	SafeStringValue(c);
+	if (rb_enc_get_index(c) && enc != rb_enc_get(c)) {
+	    c = rb_funcall(c, id_encode, 1, rb_enc_from_encoding(enc));
+	}
+	io_ungetc(RSTRING_PTR(c), RSTRING_LEN(c), fptr);
+	RB_GC_GUARD(c);
+    }
+    return Qnil;
+}
+
+VALUE
+rb_io_ungetc(VALUE io, VALUE c)
+{
+    VALUE ary = rb_check_array_type(c);
+    if (!NIL_P(ary)) {
+	rb_io_unget(RARRAY_LEN(ary), RARRAY_PTR(ary), io);
+	RB_GC_GUARD(ary);
     }
-    io_ungetc(c, fptr);
+    else {
+	rb_io_unget(1, &c, io);
+    }
+    return Qnil;
+}
+
+/*
+ *  call-seq:
+ *     ios.ungetbyte(fixnum)   => nil
+ *
+ *  Pushes back one character (passed as a parameter) onto
+ *  <em>ios</em>, such that a subsequent buffered read will return it.
+ *  See also <code>IO#ungetc</code>.
+ *
+ *     f = File.new("testfile")
+ *     c = f.getbyte    #=> 84
+ *     f.ungetbyte(c)   #=> nil
+ *     f.getbyte        #=> 84
+ */
+
+VALUE
+rb_io_ungetbyte(VALUE io, VALUE c)
+{
+    rb_io_t *fptr;
+    int cc;
+
+    GetOpenFile(io, fptr);
+    rb_io_check_readable(fptr);
+    if (NIL_P(c)) return Qnil;
+    cc = NUM2INT(c);
+    *io_unget_space(1, fptr) = (char)cc;
     return Qnil;
 }
@@ -6789,5 +6858,6 @@ Init_IO(void)
     rb_define_method(rb_cIO, "readchar",  rb_io_readchar, 0);
     rb_define_method(rb_cIO, "readbyte",  rb_io_readbyte, 0);
-    rb_define_method(rb_cIO, "ungetc",rb_io_ungetc, 1);
+    rb_define_method(rb_cIO, "ungetc", rb_io_unget, -1);
+    rb_define_method(rb_cIO, "ungetbyte", rb_io_ungetbyte, 1);
     rb_define_method(rb_cIO, "<<",    rb_io_addstr, 1);
     rb_define_method(rb_cIO, "flush", rb_io_flush, 0);


-- 
--- 僕の前にBugはない。
--- 僕の後ろにBugはできる。
    中田 伸悦

In This Thread