summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog17
-rw-r--r--array.c34
-rw-r--r--error.c3
-rw-r--r--eval.c10
-rw-r--r--hash.c9
-rw-r--r--intern.h1
-rw-r--r--re.c55
-rw-r--r--sample/test.rb2
-rw-r--r--string.c40
9 files changed, 108 insertions, 63 deletions
diff --git a/ChangeLog b/ChangeLog
index 19a04fcad2..25de42253f 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,20 @@
+Mon Feb 3 13:18:05 2003 Yukihiro Matsumoto <matz@ruby-lang.org>
+
+ * re.c (rb_memsearch): algolithm body of String#index.
+
+ * error.c (Init_Exception): "to_str" removed.
+
+ * eval.c (eval): should not rely on Exception#to_str
+
+ * eval.c (compile_error): ditto.
+
+ * error.c (err_append): ditto.
+
+Sat Feb 1 23:56:29 2003 Yukihiro Matsumoto <matz@ruby-lang.org>
+
+ * hash.c (rb_hash_merge): Hash#merge, non destructive "update".
+ now there's also Hash#merge! which is an alias to "update".
+
Fri Jan 31 14:16:59 2003 Yukihiro Matsumoto <matz@ruby-lang.org>
* string.c (rb_str_index): search using Karp-Rabin algolithm.
diff --git a/array.c b/array.c
index 8151925b7e..7e039abf6a 100644
--- a/array.c
+++ b/array.c
@@ -1649,23 +1649,6 @@ rb_ary_cmp(ary1, ary2)
}
static VALUE
-rb_ary_diff(ary1, ary2)
- VALUE ary1, ary2;
-{
- VALUE ary3;
- long i;
-
- ary2 = to_ary(ary2);
- ary3 = rb_ary_new();
- for (i=0; i<RARRAY(ary1)->len; i++) {
- if (rb_ary_includes(ary2, RARRAY(ary1)->ptr[i])) continue;
- if (rb_ary_includes(ary3, RARRAY(ary1)->ptr[i])) continue;
- rb_ary_push(ary3, RARRAY(ary1)->ptr[i]);
- }
- return ary3;
-}
-
-static VALUE
ary_make_hash(ary1, ary2)
VALUE ary1, ary2;
{
@@ -1684,6 +1667,23 @@ ary_make_hash(ary1, ary2)
}
static VALUE
+rb_ary_diff(ary1, ary2)
+ VALUE ary1, ary2;
+{
+ VALUE ary3, hash;
+ long i;
+
+ hash = ary_make_hash(to_ary(ary2), 0);
+ ary3 = rb_ary_new();
+
+ for (i=0; i<RARRAY(ary1)->len; i++) {
+ if (st_lookup(RHASH(hash)->tbl, RARRAY(ary1)->ptr[i], 0)) continue;
+ rb_ary_push(ary3, RARRAY(ary1)->ptr[i]);
+ }
+ return ary3;
+}
+
+static VALUE
rb_ary_and(ary1, ary2)
VALUE ary1, ary2;
{
diff --git a/error.c b/error.c
index 468fbb6d13..8b6b324954 100644
--- a/error.c
+++ b/error.c
@@ -544,7 +544,6 @@ Init_Exception()
rb_define_method(rb_eException, "exception", exc_exception, -1);
rb_define_method(rb_eException, "initialize", exc_initialize, -1);
rb_define_method(rb_eException, "to_s", exc_to_s, 0);
- rb_define_method(rb_eException, "to_str", exc_to_s, 0);
rb_define_method(rb_eException, "message", exc_to_s, 0);
rb_define_method(rb_eException, "inspect", exc_inspect, 0);
rb_define_method(rb_eException, "backtrace", exc_backtrace, 0);
@@ -1115,7 +1114,7 @@ err_append(s)
ruby_errinfo = rb_exc_new2(rb_eSyntaxError, s);
}
else {
- VALUE str = rb_str_to_str(ruby_errinfo);
+ VALUE str = rb_obj_as_string(ruby_errinfo);
rb_str_cat2(str, "\n");
rb_str_cat2(str, s);
diff --git a/eval.c b/eval.c
index aedcefcf74..dc26c1c4a8 100644
--- a/eval.c
+++ b/eval.c
@@ -1351,7 +1351,7 @@ compile_error(at)
}
rb_str_buf_cat(str, "\n", 1);
if (!NIL_P(ruby_errinfo)) {
- rb_str_append(str, ruby_errinfo);
+ rb_str_append(str, rb_obj_as_string(ruby_errinfo));
}
rb_exc_raise(rb_exc_new3(rb_eSyntaxError, str));
}
@@ -5176,18 +5176,18 @@ eval(self, src, scope, file, line)
ruby_set_current_source();
if (state) {
if (state == TAG_RAISE) {
- VALUE err;
- VALUE errat;
+ VALUE err, errat, mesg;
+ mesg = rb_obj_as_string(ruby_errinfo);
if (strcmp(file, "(eval)") == 0) {
if (ruby_sourceline > 1) {
errat = get_backtrace(ruby_errinfo);
err = rb_str_dup(RARRAY(errat)->ptr[0]);
rb_str_cat2(err, ": ");
- rb_str_append(err, ruby_errinfo);
+ rb_str_append(err, mesg);
}
else {
- err = rb_str_dup(ruby_errinfo);
+ err = mesg;
}
rb_exc_raise(rb_funcall(ruby_errinfo, rb_intern("exception"), 1, err));
}
diff --git a/hash.c b/hash.c
index 249bc645a5..d52ef7a40c 100644
--- a/hash.c
+++ b/hash.c
@@ -937,6 +937,13 @@ rb_hash_update(hash1, hash2)
return hash1;
}
+static VALUE
+rb_hash_merge(hash1, hash2)
+ VALUE hash1, hash2;
+{
+ return rb_hash_update(rb_obj_dup(hash1), hash2);
+}
+
static int path_tainted = -1;
static char **origenviron;
@@ -1743,6 +1750,8 @@ Init_Hash()
rb_define_method(rb_cHash,"invert", rb_hash_invert, 0);
rb_define_method(rb_cHash,"update", rb_hash_update, 1);
rb_define_method(rb_cHash,"replace", rb_hash_replace, 1);
+ rb_define_method(rb_cHash,"merge!", rb_hash_update, 1);
+ rb_define_method(rb_cHash,"merge", rb_hash_merge, 1);
rb_define_method(rb_cHash,"include?", rb_hash_has_key, 1);
rb_define_method(rb_cHash,"member?", rb_hash_has_key, 1);
diff --git a/intern.h b/intern.h
index 46980dfc43..1ed37a82ec 100644
--- a/intern.h
+++ b/intern.h
@@ -330,6 +330,7 @@ VALUE rb_length_by_each _((VALUE));
/* re.c */
int rb_memcmp _((char*,char*,long));
int rb_memcicmp _((char*,char*,long));
+int rb_memsearch _((char*,long,char*,long));
VALUE rb_reg_nth_defined _((int, VALUE));
VALUE rb_reg_nth_match _((int, VALUE));
VALUE rb_reg_last_match _((VALUE));
diff --git a/re.c b/re.c
index 3ddfb30d77..8828119728 100644
--- a/re.c
+++ b/re.c
@@ -96,6 +96,59 @@ rb_memcmp(p1, p2, len)
return rb_memcicmp(p1, p2, len);
}
+int
+rb_memsearch(x0, m, y0, n)
+ char *x0, *y0;
+ long m, n;
+{
+ unsigned char *x = x0, *y = y0;
+ unsigned char *s, *e;
+ long d, i;
+ unsigned long hx, hy;
+
+#define KR_REHASH(a, b, h) ((((h) - (a)*d) << 1) + (b))
+
+ s = y; e = s + n - m + 1;
+
+ /* Preprocessing */
+ /* computes d = 2^(m-1) with
+ the left-shift operator */
+ for (d = i = 1; i < m; ++i)
+ d = (d<<1);
+
+ if (ruby_ignorecase) {
+ /* Prepare hash value */
+ for (hy = hx = i = 0; i < m; ++i) {
+ hx = ((hx<<1) + casetable[x[i]]);
+ hy = ((hy<<1) + casetable[s[i]]);
+ }
+ /* Searching */
+ while (s < e) {
+ if (hx == hy && rb_memcicmp(x, s, m) == 0) {
+ return s-y;
+ }
+ hy = KR_REHASH(casetable[*s], casetable[*(s+m)], hy);
+ s++;
+ }
+ }
+ else {
+ /* Prepare hash value */
+ for (hy = hx = i = 0; i < m; ++i) {
+ hx = ((hx<<1) + x[i]);
+ hy = ((hy<<1) + s[i]);
+ }
+ /* Searching */
+ while (s < e) {
+ if (hx == hy && memcmp(x, s, m) == 0) {
+ return s-y;
+ }
+ hy = KR_REHASH(*s, *(s+m), hy);
+ s++;
+ }
+ }
+ return -1;
+}
+
#define REG_CASESTATE FL_USER0
#define KCODE_NONE 0
#define KCODE_EUC FL_USER1
@@ -469,7 +522,7 @@ rb_reg_kcode_m(re)
case KCODE_UTF8:
kcode = "utf8"; break;
default:
- rb_bug("unknow kcode - should not happen");
+ rb_bug("unknown kcode - should not happen");
break;
}
return rb_str_new2(kcode);
diff --git a/sample/test.rb b/sample/test.rb
index c47ceedd43..4b0099058c 100644
--- a/sample/test.rb
+++ b/sample/test.rb
@@ -1228,7 +1228,7 @@ if defined? Process.kill
rescue
x = $!
end
- test_ok(x && /Interrupt/ =~ x)
+ test_ok(x && /Interrupt/ =~ x.message)
end
test_check "eval"
diff --git a/string.c b/string.c
index c864f1fc11..90449023c6 100644
--- a/string.c
+++ b/string.c
@@ -838,48 +838,14 @@ rb_str_index(str, sub, offset)
VALUE str, sub;
long offset;
{
- char *s, *e, *p;
- long len;
- int d, hx, hy, i;
-
if (offset < 0) {
offset += RSTRING(str)->len;
if (offset < 0) return -1;
}
if (RSTRING(str)->len - offset < RSTRING(sub)->len) return -1;
- s = RSTRING(str)->ptr+offset;
- p = RSTRING(sub)->ptr;
- len = RSTRING(sub)->len;
- if (len == 0) return offset;
- e = RSTRING(str)->ptr + RSTRING(str)->len - len + 1;
-
- /* seach using Karp-Rabin algolithm described in:
-
- EXACT STRING MATCHING ALGORITHMS
- http://www-igm.univ-mlv.fr/~lecroq/string/index.html
- */
-
-#define KR_REHASH(a, b, h) ((((h) - (a)*d) << 1) + (b))
-
- /* Preprocessing */
- /* computes d = 2^(m-1) with
- the left-shift operator */
- for (d = i = 1; i < len; ++i)
- d = (d<<1);
-
- for (hy = hx = i = 0; i < len; ++i) {
- hx = ((hx<<1) + p[i]);
- hy = ((hy<<1) + s[i]);
- }
-
- /* Searching */
- while (s < e) {
- if (hx == hy && rb_memcmp(p, s, len) == 0)
- return (s-(RSTRING(str)->ptr));
- hy = KR_REHASH(*s, *(s+len), hy);
- s++;
- }
- return -1;
+ if (RSTRING(sub)->len == 0) return offset;
+ return rb_memsearch(RSTRING(sub)->ptr, RSTRING(sub)->len,
+ RSTRING(str)->ptr+offset, RSTRING(str)->len-offset);
}
static VALUE