簡體   English   中英

Ruby 中的冒號運算符是什么?

[英]What is the colon operator in Ruby?

當我說{:bla => 1, :bloop => 2 }時, :到底是做什么的? 我在某處讀到它與字符串的相似之處,但不知何故是一個符號。

我對這個概念不是很清楚,有人可以啟發我嗎?

:foo是一個名為“foo”的符號。 符號有一個顯着的特點,即任何兩個同名的符號都是相同的:

"foo".equal? "foo"  # false
:foo.equal? :foo    # true

這使得比較兩個符號非常快(因為只涉及指針比較,而不是像在字符串中比較所有字符),而且您不會有無數個相同符號的副本浮動。

此外,與字符串不同,符號是不可變的。

只是為了證明答案中提到的一些事情:

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)

就速度而言,兩種符號測試基本相同。 在 1,000,000 次迭代之后,只有 0.004733 秒的差異,所以我會說這是一個可以使用的洗滌。

符號是在 ruby 中表示字符串和名稱的一種方式。

符號和字符串的主要區別在於,在 ruby 的 session 期間,同名的符號在 memory 中只存在一次。

當您需要使用相同的詞來表示不同的事物時,它們很有用

著名書籍Agile Web Development with Rails中有一些引述,這也可能有助於理解符號

Rails 使用符號來識別事物。 特別是,它在命名方法參數和在哈希中查找內容時將它們用作鍵。

redirect_to :action => "edit", :id => params[:id]

您可以將符號視為神奇地變成常量的字符串文字。 或者,您可以認為冒號表示“命名的事物”,因此:id 是“命名為 id 的事物”。

在 ruby 中,每個 object 都有一個唯一的 object 標識符,如果你寫puts "hello".object_id :hello.object_id你的 irb 中並點擊返回 2 次不同的時間,你會得到 hello:.2 不同的返回值只得到相同的一個返回值。 這應該解釋了差異。

如果你使用:foo => bar , foo 將是一個符號。 符號的好處是它們是獨一無二的。 當您調用 hash 中的項目時,您執行hash[:foo]

與字符串相比,符號需要更少的 memory,如果您想讓程序更快一點,它們也很有用。

所有這些答案都省略了一個額外的誘人細節..如果您將符號串起來:foo,您會得到..猜猜是什么..字符串“foo”。 因此

irb(main):025:0>
irb(main):026:0> :foo
=> :foo
irb(main):027:0> "#{:foo}"
=> "foo"
irb(main):028:0>
irb(main):029:0> 'foo' <=> :foo
=> nil
irb(main):030:0> 'foo' <=> :foo.to_s
=> 0
irb(main):031:0>

因此.. 對於 Perl 程序員.. 這是 Ruby 對“裸詞”的回答。

這是一個象征。 基本上,您是說 hash 的兩個元素具有鍵blabloop ,就像您使用了字符串"bla""bloop" 但是,它們占用的 memory 比字符串少,並且更易於鍵入。

如果您熟悉 Java,您可能知道 Java 中的字符串是不可變的。 Ruby 中的符號在這個意義上是相似的。 它們是不可變的,即特定符號的任意數量出現:symbol將 map 到僅單個 memory 地址。 因此,建議盡可能使用符號,因為它優化了 memory 的使用。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM