Hash#inspect with colon style
This commit is contained in:
parent
2c0149d330
commit
a8a0591253
Notes:
git
2024-10-03 09:47:30 +00:00
47
hash.c
47
hash.c
@ -3405,20 +3405,65 @@ rb_hash_to_a(VALUE hash)
|
|||||||
return ary;
|
return ary;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool
|
||||||
|
symbol_key_needs_quote(VALUE str)
|
||||||
|
{
|
||||||
|
long len = RSTRING_LEN(str);
|
||||||
|
if (len == 0 || !rb_str_symname_p(str)) return true;
|
||||||
|
const char *s = RSTRING_PTR(str);
|
||||||
|
char first = s[0];
|
||||||
|
if (first == '@' || first == '$' || first == '!') return true;
|
||||||
|
if (!at_char_boundary(s, s + len - 1, RSTRING_END(str), rb_enc_get(str))) return false;
|
||||||
|
switch (s[len - 1]) {
|
||||||
|
case '+':
|
||||||
|
case '-':
|
||||||
|
case '*':
|
||||||
|
case '/':
|
||||||
|
case '`':
|
||||||
|
case '%':
|
||||||
|
case '^':
|
||||||
|
case '&':
|
||||||
|
case '|':
|
||||||
|
case ']':
|
||||||
|
case '<':
|
||||||
|
case '=':
|
||||||
|
case '>':
|
||||||
|
case '~':
|
||||||
|
case '@':
|
||||||
|
return true;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
inspect_i(VALUE key, VALUE value, VALUE str)
|
inspect_i(VALUE key, VALUE value, VALUE str)
|
||||||
{
|
{
|
||||||
VALUE str2;
|
VALUE str2;
|
||||||
|
|
||||||
|
bool is_symbol = SYMBOL_P(key);
|
||||||
|
bool quote = false;
|
||||||
|
if (is_symbol) {
|
||||||
|
str2 = rb_sym2str(key);
|
||||||
|
quote = symbol_key_needs_quote(str2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
str2 = rb_inspect(key);
|
str2 = rb_inspect(key);
|
||||||
|
}
|
||||||
if (RSTRING_LEN(str) > 1) {
|
if (RSTRING_LEN(str) > 1) {
|
||||||
rb_str_buf_cat_ascii(str, ", ");
|
rb_str_buf_cat_ascii(str, ", ");
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
rb_enc_copy(str, str2);
|
rb_enc_copy(str, str2);
|
||||||
}
|
}
|
||||||
|
if (quote) {
|
||||||
|
rb_str_buf_append(str, rb_str_inspect(str2));
|
||||||
|
}
|
||||||
|
else {
|
||||||
rb_str_buf_append(str, str2);
|
rb_str_buf_append(str, str2);
|
||||||
rb_str_buf_cat_ascii(str, "=>");
|
}
|
||||||
|
|
||||||
|
rb_str_buf_cat_ascii(str, is_symbol ? ": " : " => ");
|
||||||
str2 = rb_inspect(value);
|
str2 = rb_inspect(value);
|
||||||
rb_str_buf_append(str, str2);
|
rb_str_buf_append(str, str2);
|
||||||
|
|
||||||
|
@ -869,6 +869,33 @@ class TestHash < Test::Unit::TestCase
|
|||||||
$, = nil
|
$, = nil
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def test_inspect
|
||||||
|
no_quote = '{a: 1, a!: 1, a?: 1}'
|
||||||
|
quote0 = '{"": 1}'
|
||||||
|
quote1 = '{"0": 1, "!": 1, "%": 1, "&": 1, "*": 1, "+": 1, "-": 1, "/": 1, "<": 1, ">": 1, "^": 1, "`": 1, "|": 1, "~": 1}'
|
||||||
|
quote2 = '{"@a": 1, "$a": 1, "+@": 1, "a=": 1, "[]": 1}'
|
||||||
|
quote3 = '{"a\"b": 1, "@@a": 1, "<=>": 1, "===": 1, "[]=": 1}'
|
||||||
|
assert_equal(no_quote, eval(no_quote).inspect)
|
||||||
|
assert_equal(quote0, eval(quote0).inspect)
|
||||||
|
assert_equal(quote1, eval(quote1).inspect)
|
||||||
|
assert_equal(quote2, eval(quote2).inspect)
|
||||||
|
assert_equal(quote3, eval(quote3).inspect)
|
||||||
|
begin
|
||||||
|
enc = Encoding.default_external
|
||||||
|
Encoding.default_external = Encoding::ASCII
|
||||||
|
utf8_ascii_hash = '{"\\u3042": 1}'
|
||||||
|
assert_equal(eval(utf8_ascii_hash).inspect, utf8_ascii_hash)
|
||||||
|
Encoding.default_external = Encoding::UTF_8
|
||||||
|
utf8_hash = "{\u3042: 1}"
|
||||||
|
assert_equal(eval(utf8_hash).inspect, utf8_hash)
|
||||||
|
Encoding.default_external = Encoding::Windows_31J
|
||||||
|
sjis_hash = "{\x87]: 1}".force_encoding('sjis')
|
||||||
|
assert_equal(eval(sjis_hash).inspect, sjis_hash)
|
||||||
|
ensure
|
||||||
|
Encoding.default_external = enc
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
def test_update
|
def test_update
|
||||||
h1 = @cls[ 1 => 2, 2 => 3, 3 => 4 ]
|
h1 = @cls[ 1 => 2, 2 => 3, 3 => 4 ]
|
||||||
h2 = @cls[ 2 => 'two', 4 => 'four' ]
|
h2 = @cls[ 2 => 'two', 4 => 'four' ]
|
||||||
|
Loading…
x
Reference in New Issue
Block a user