当我说{:bla => 1,:bloop => 2}时,:到底做什么?我在什么地方读到过,它与字符串相似,但某种程度上是一个符号。
我对这个概念不是很清楚,有人能给我一些启发吗?
当我说{:bla => 1,:bloop => 2}时,:到底做什么?我在什么地方读到过,它与字符串相似,但某种程度上是一个符号。
我对这个概念不是很清楚,有人能给我一些启发吗?
当前回答
在ruby中,每个对象都有一个唯一的对象标识符,如果你写入“hello”。Object_id在你的irb和点击返回2次不同的,你将得到2个不同的返回值,但如果你写:hello。Object_id 2次,只能得到相同的返回值。 这应该可以解释这种差异。
其他回答
如果您熟悉Java,您可能知道Java中的字符串是不可变的。Ruby中的符号在这个意义上是类似的。它们是不可变的,也就是说,任何特定符号的出现次数:symbol将只映射到单个内存地址。因此,建议尽可能使用符号,因为这样可以优化内存使用。
:foo是一个名为“foo”的符号。符号有一个明显的特征,任何两个命名相同的符号都是相同的:
"foo".equal? "foo" # false
:foo.equal? :foo # true
这使得比较两个符号非常快(因为只涉及指针比较,而不是像在字符串中那样比较所有字符),而且你不会有无数个相同符号的副本。
另外,与字符串不同,符号是不可变的。
在ruby中,每个对象都有一个唯一的对象标识符,如果你写入“hello”。Object_id在你的irb和点击返回2次不同的,你将得到2个不同的返回值,但如果你写:hello。Object_id 2次,只能得到相同的返回值。 这应该可以解释这种差异。
只是为了证明答案中提到的一些事情:
require 'benchmark'
n = 1_000_000
print '"foo".equal? "foo" -> ', ("foo".equal? "foo"), "\n"
print '"foo" == "foo" -> ', ("foo" == "foo" ), "\n"
print ':foo.equal? :foo -> ', (:foo.equal? :foo ), "\n"
print ':foo == :foo -> ', (:foo == :foo ), "\n"
Benchmark.bm(10) do |b|
b.report('string') { n.times { "foo".equal? "foo" }}
b.report('str == str') { n.times { "foo" == "foo" }}
b.report('symbol') { n.times { :foo.equal? :foo }}
b.report('sym == sym') { n.times { :foo == :foo }}
end
运行它输出:
"foo".equal? "foo" -> false
"foo" == "foo" -> true
:foo.equal? :foo -> true
:foo == :foo -> true
那么,用equal来比较字符串和字符串?失败是因为它们是不同的对象,即使它们的内容相同。==比较内容,用符号进行等效检查要快得多。
user system total real
string 0.370000 0.000000 0.370000 ( 0.371700)
str == str 0.330000 0.000000 0.330000 ( 0.326368)
symbol 0.170000 0.000000 0.170000 ( 0.174641)
sym == sym 0.180000 0.000000 0.180000 ( 0.179374)
两种符号测试在速度方面基本相同。在100万次迭代之后,只有0.004733秒的差异,所以我认为这是一次洗涤。
符号是一种在ruby中表示字符串和名称的方法。
符号和字符串之间的主要区别是,相同名称的符号在ruby会话期间只在内存中存在一次。
当你需要用同一个词来表示不同的东西时,它们很有用