Ruby 4.0.0 preview3 發布

naruse 發表於 2025-12-18
翻譯: Bear Su

我們很高興宣布 Ruby 4.0.0-preview3 發布了。 Ruby 4.0 導入了 Ruby::Box 和 “ZJIT”,以及其他改進功能。

Ruby::Box

這是一項用來提供定義區隔的(實驗性質)新功能。 關於「Ruby Box」的詳細資訊,請參閱doc/language/box.md。 [Feature #21311] [Misc #21385]

語法變更

  • *nil 不再呼叫 nil.to_a,就跟 **nil 不呼叫 nil.to_hash 一樣。[Feature #21047]

  • 位於行首的邏輯二元運算子(||&&andor)會延續前一行的內容,如同 fluent dot。 以下兩段程式碼是相同的效果:

      if condition1
         && condition2
        ...
      end
    
      if condition1 && condition2
        ...
      end
    

    [Feature #20925]

核心類別更新

注意:我們只列出特別的類別更新。

  • Kernel

    • Kernel#inspect 現在會檢查是否存在 #instance_variables_to_inspect 方法,這讓開發者可以控制哪些實體變數(instance variables)可以顯示在 #inspect 的字串中:

        class DatabaseConfig
          def initialize(host, user, password)
            @host = host
            @user = user
            @password = password
          end
      
          private def instance_variables_to_inspect = [:@host, :@user]
        end
      
        conf = DatabaseConfig.new("localhost", "root", "hunter2")
        conf.inspect #=> #<DatabaseConfig:0x0000000104def350 @host="localhost", @user="root">
      

      [Feature #21219]

    • 移除被棄用的行為:透過 Kernel#open 並在開頭使用 | 符號來建立 process。 [Feature #19630]

  • Binding

    • Binding#local_variables 不再包含編號參數。 同時,Binding#local_variable_getBinding#local_variable_set 也不再處理編號參數。 [Bug #21049]
  • File

    • File::Stat#birthtime 現在可在核心與系統支援 statx 系統呼叫 的 Linux 上使用。 [Feature #21205]
  • IO

    • IO.select 允許 Float::INFINITY 作為逾時參數。 [Feature #20610]

    • 移除被棄用的行為:透過 IO 並在開頭使用 | 符號來建立行程 [Feature #19630]

  • Math

  • Method

    • Method#source_locationProc#source_locationUnboundMethod#source_location 現在會回傳 5 個元素的擴展位置資訊:[path, start_line, start_column, end_line, end_column]。先前 2 個元素的格式 [path, line] 仍可透過對結果呼叫 .take(2) 來取得。 [Feature #6012]
  • Proc

    • Proc#parameters 現在會將匿名可選參數顯示為 [:opt] 而非 [:opt, nil],使得其輸出與匿名參數為必要時的格式保持一致。 [Bug #20974]
  • Ractor

    • 新增了 Ractor::Port 類別,為 Ractor 之間的通訊提供了一種新的同步機制。 [Feature #21262]
        port1 = Ractor::Port.new
        port2 = Ractor::Port.new
        Ractor.new port1, port2 do |port1, port2|
          port1 << 1
          port2 << 11
          port1 << 2
          port2 << 12
        end
        2.times{ p port1.receive } #=> 1, 2
        2.times{ p port2.receive } #=> 11, 12
      

      Ractor::Port 提供以下方法:

      • Ractor::Port#receive
      • Ractor::Port#send (或 Ractor::Port#<<)
      • Ractor::Port#close
      • Ractor::Port#closed?

      最後移除了 Ractor.yieldRactor#take

    • 新增了 Ractor#joinRactor#value 用於等待 Ractor 終止。這些方法與 Thread#joinThread#value 類似。

    • 新增了 Ractor#monitorRactor#unmonitor,作為內部實作 Ractor#join 時所使用的低階介面。

    • Ractor.select 現在僅接受 Ractors 與 Ports。若傳入的是 Ractors,它會在該 Ractor 終止時回傳。

    • 新增了 Ractor#default_port。每個 Ractor 都有一個預設埠,供 Ractor.sendRactor.receive 使用。

    • 移除了 Ractor#close_incomingRactor#close_outgoing

    • 導入了 Ractor.shareable_procRactor.shareable_lambda 以建立共享的 Proc 或 lambda。 [Feature #21550], [Feature #21557]
  • Range

    • Range#to_setEnumerator#to_set 現在會進行大小檢查,以避免發生無窮範圍的問題。 [Bug #21654]

    • Range#overlap? 現在能正確處理無限(無邊界)範圍。 [Bug #21185]

    • 已修正 Range#max 對於無開頭整數範圍的行為。 [Bug #21174] [Bug #21175]。

  • Ruby

    • 定義了一個新的頂層模組 Ruby,其中包含與 Ruby 相關的常數。此模組在 Ruby 3.4 中已被預留,現在則是正式定義。 [Feature #20884]
  • Ruby::Box

  • Set

    • Set 現在是核心類別,而非自動載入的標準函式庫類別。 [Feature #21216]

    • Set#inspect 現在回傳適合用於 eval 的字串,並使用 Set[] 語法(例如:使用 Set[1, 2, 3] 而非 #<Set: {1, 2, 3}>)。這讓它與 Array 和 Hash 等其他核心集合類別保持一致。 [Feature #21389]

    • Set#to_setEnumerable#to_set 傳遞參數的行為現在已被棄用。 [Feature #21390]

  • Socket

    • Socket.tcpTCPSocket.new 現在接受 open_timeout 關鍵字參數,可用於指定建立初始連線時的逾時時間。 [Feature #21347]
  • String

  • Thread

    • 導入了 Thread#raise(cause:) 參數支援,與 Kernel#raise 的用法類似。 [Feature #21360]
  • Fiber

    • 導入了 Fiber#raise(cause:) 參數支援,與 Kernel#raise 的用法類似。 [Feature #21360]
  • Fiber::Scheduler

    • 導入了 Fiber::Scheduler#fiber_interrupt,可用於拋出特定的例外來中斷 fiber。 最初的使用案例是當 IO 操作關閉時,用來中斷正在等待該阻塞 IO 操作的 fiber。 [Feature #21166]
  • Pathname

    • Pathname 已從預設 gem 升級為 Ruby 的核心類別。 [Feature #17473]

標準函式庫更新

以下預設 gem 變更為隨附 gem:

  • ostruct 0.6.3
  • pstore 0.2.0
  • benchmark 0.5.0
  • logger 1.7.0
  • rdoc 6.17.0
  • win32ole 1.9.2
  • irb 1.16.0
  • reline 0.6.3
  • readline 0.0.4
  • fiddle 1.1.8

我們只列出特別的標準函式庫更新。

其他變更列於以下章節。 若該項目在 GitHub 上有提供發布紀錄,我們也列出了從前一個隨附版本(即 Ruby 3.3.0)以來的發布歷史。

新增了以下預設 gem。

  • win32-registry 0.1.2

更新了以下預設 gem。

  • RubyGems 4.0.2
  • bundler 4.0.2
  • date 3.5.1
  • digest 3.2.1
  • english 0.8.1
  • erb 6.0.1
  • etc 1.4.6
  • fcntl 1.3.0
  • fileutils 1.8.0
  • forwardable 1.4.0
  • io-console 0.8.2
  • io-nonblock 0.3.2
  • io-wait 0.4.0
  • ipaddr 1.2.8
  • json 2.18.0
  • net-http 0.9.1
  • openssl 4.0.0
  • optparse 0.8.1
  • pp 0.6.3
  • prism 1.6.0
  • psych 5.3.1
  • resolv 0.7.0
  • stringio 3.2.0
  • strscan 3.1.6
  • time 0.4.2
  • timeout 0.6.0
  • uri 1.1.1
  • weakref 0.1.4
  • zlib 3.2.2

更新了以下隨附 gem。

  • minitest 5.27.0
  • power_assert 3.0.1
  • rake 13.3.1
  • test-unit 3.7.3
  • rexml 3.4.4
  • net-ftp 0.3.9
  • net-imap 0.6.1
  • net-smtp 0.5.1
  • matrix 0.4.3
  • prime 0.1.4
  • rbs 3.10.0.pre.2
  • typeprof 0.31.0
  • debug 1.11.0
  • base64 0.3.0
  • bigdecimal 4.0.1
  • drb 2.2.3
  • syslog 0.3.0
  • csv 3.3.5
  • repl_type_completor 0.1.12

支援的平台

  • Windows

    • 停止支援低於 14.0 (_MSC_VER 1900) 的 MSVC 版本。這意味著現在需要使用 Visual Studio 2015 或更新版本。

相容性問題

  • 由於新增了 Ractor::Port,下列方法已從 Ractor 中移除:

    • Ractor.yield
    • Ractor#take
    • Ractor#close_incoming
    • Ractor#close_outgoging

    [Feature #21262]

  • ObjectSpace._id2ref 已被棄用。 [Feature #15408]

  • Process::Status#&Process::Status#>> 已被移除。 它們在 Ruby 3.3. 被棄用。 [Bug #19868]

  • rb_path_check 已被移除。 此函數曾用在已於 Ruby 2.7 移除的 $SAFE 路徑檢查,且此函數先前就已被棄用。 [Feature #20971]

標準函式庫相容問題

  • CGI 函式庫已從預設 gem 中移除。現在僅針對以下方法提供 cgi/escape

    • CGI.escapeCGI.unescape
    • CGI.escapeHTMLCGI.unescapeHTML
    • CGI.escapeURIComponentCGI.unescapeURIComponent
    • CGI.escapeElementCGI.unescapeElement

    [Feature #21258]

  • 隨著 Set 從標準函式庫移至核心類別,set/sorted_set.rb 已被移除,且 SortedSet 不再是自動載入的常數。 若要使用 SortedSet,請安裝 sorted_set gem 並執行 require 'sorted_set'。 [Feature #21287]

C API 更新

  • IO

    • rb_thread_fd_close 已被棄用,現在沒有作用。如果您需要從 C 擴充功能將檔案描述符提供給 Ruby 程式碼,請使用 RUBY_IO_MODE_EXTERNAL 建立一個 IO 實體,並使用 rb_io_close(io) 來關閉它(這同時會中斷並等待該 IO 實體上所有進行中的操作)。 直接關閉檔案描述符不會中斷進行中的操作,且可能導致未定義行為。 換句話說,如果兩個 IO 物件共享同一個檔案描述符,關閉其中一個並不會影響另一個。 [Feature #18455]
  • GVL

    • rb_thread_call_with_gvl 現在不論是否持有 GVL 均可運作。這讓 gems 可以不必再檢查 ruby_thread_has_gvl_p。 在使用 GVL 時仍請保持謹慎。 [Feature #20750]
  • Set

    • 已新增 Set 的 C API。支援以下方法: [Feature #21459]

      • rb_set_foreach
      • rb_set_new
      • rb_set_new_capa
      • rb_set_lookup
      • rb_set_add
      • rb_set_clear
      • rb_set_delete
      • rb_set_size

實作改進

Ractor

投入了大量心力來提升 Ractor 的穩定性、效能與易用性。這些改進使得 Ractor 的實作更接近脫離實驗性質的狀態。

  • 效能提升
    • 凍結字串與符號表在內部使用無鎖雜湊集合。
    • 方法快取查詢在多數情況下避免了鎖定。
    • 類別(以及 geniv)的實體變數存取速度更快,並避免了鎖定。
    • 在分配物件時,避免了快取衝突。
    • object_id 在多數情況下避免了鎖定。
  • 修復錯誤與可靠性
    • 修正了同時使用 Ractor 與 Thread 時可能發生的死鎖。
    • 修正了在 Ractor 中使用 require 與 autoload 的問題。
    • 修正了跨 Ractor 的編碼與轉碼問題。
    • 修正了垃圾回收操作與方法失效時的競爭條件。
    • 修正了啟動 Ractor 後,行程進行複製時的問題。

JIT

  • ZJIT
    • 若要啟用 --zjit 支援,請使用 Rust 1.85.0 或更新版本來編譯 Ruby。
    • 在 Ruby 4.0.0,ZJIT 的速度已超越直譯器,但尚未達到 YJIT 的水準。我們鼓勵大家嘗試 ZJIT,但目前建議不要將其部署於正式環境。
    • 我們的目標是在 Ruby 4.1 中讓 ZJIT 的速度超越 YJIT,並達到可供正式環境使用的水準。
  • YJIT
    • RubyVM::YJIT.runtime_stats
      • ratio_in_yjit 不再於預設建置中運作。 請使用 --enable-yjit=statsconfigure 中啟用 --yjit-stats
      • 預設統計新增 invalidate_everything,當所有程式碼被 TracePoint 無效化時遞增。
    • RubyVM::YJIT.enable 新增 mem_size:call_threshold: 選項。
  • RJIT
    • 移除 --rjit。我們將把第三方 JIT API 的實作移至 ruby/rjit 儲存庫。

其他變更

參見 NEWScommit logs 來了解更多。

自 Ruby 3.4.0 以來,計 3776 檔案變更,222800 行新增(+),293617 行刪減(-)!

下載

  • https://cache.ruby-lang.org/pub/ruby/4.0/ruby-4.0.0-preview3.tar.gz

    SIZE: 23865890
    SHA1: a348f196e0314d8863ae5d5f0a588a37c52aa89c
    SHA256: 43d0926e776fbd5599adcc7bccb4ccc804e109f402a2068607a2a86562c2cdc0
    SHA512: 1c7f10405832646eceacb278ea7cc3445dc0e1778e9a9331062f2fb0164d45ba5af0b4244dc6ae46e36730d6cafb4c4196fbd4f4fb74029afde5ecf4fd433a6b
    
  • https://cache.ruby-lang.org/pub/ruby/4.0/ruby-4.0.0-preview3.tar.xz

    SIZE: 17915004
    SHA1: b7b99831558b9cd6cf8fb148f07cd4e8e59d9e99
    SHA256: 8d7a503b2c4abcfacf0fa54ac56d37f7dd6d643a3a717661729cabbe947610a6
    SHA512: b046c015a58daafb1640d8db62a36ebf64c7f83fbfb033fa327458afab6e9c31b1c2b194b347fd63f16e413e732d3e6ac20076282b433ef16923343c9ed84aa1
    
  • https://cache.ruby-lang.org/pub/ruby/4.0/ruby-4.0.0-preview3.zip

    SIZE: 29403010
    SHA1: 689cb6c497afb96d26745708e772b63afca52e1a
    SHA256: c29147727a8eacf01b942012e3d6fa26010f98f43f6ab249c391f47c744f44cf
    SHA512: c07d6069b391e38ec99725201d021998ccfb913423636f729eccd0cff17cb9ab7e8565f46d68eea96cf7f546cee647892ca3f37b720a202e8e5496cd10dd168b
    

Ruby 是什麼

Ruby 最初由 Matz(Yukihiro Matsumoto)於 1993 年開發的開源軟體。可以在許多平台上執行。使用者來自世界各地,特別活躍於網路開發領域。

最新消息

Ruby 4.0.0 發布

我們很高興宣布 Ruby 4.0.0 發布了。 Ruby 4.0 導入了 Ruby::Box 和 “ZJIT”,以及許多改進功能。

naruse 發表於 2025-12-25

Ruby 文件的新樣貌

繼重新設計 ruby-lang.org 之後,我們還有更多消息來慶祝 Ruby 誕生 30 週年: docs.ruby-lang.org 採用了 Aliki—RDoc’s 的全新預設主題。

Stan Lo 發表於 2025-12-23

重新設計我們的網站形象

我們很興奮地宣布網站進行了全面改版。這次更新的設計方案是由 Taeko Akatsuka 負責創作。

Hiroshi SHIBATA 發表於 2025-12-22

更多新聞...