Ruby 3.1.0 的 NEWS¶ ↑
本文档列出了自 3.0.0 版本以来,除了错误修复之外的用户可见的功能变更。
请注意,每个条目都保持在最低限度,详细信息请参阅链接。
语言变更¶ ↑
-
如果块仅传递给另一个方法,则块参数现在可以是匿名的。[功能 #11256]
def foo(&) bar(&) end
-
Pin 操作符现在接受一个表达式。[功能 #17411]
Prime.each_cons(2).lazy.find_all{_1 in [n, ^(n + 2)]}.take(3).to_a #=> [[3, 5], [5, 7], [11, 13]]
-
Pin 操作符现在支持实例、类和全局变量。[功能 #17724]
@n = 5 Prime.each_cons(2).lazy.find{_1 in [n, ^@n]} #=> [3, 5]
-
单行模式匹配不再是实验性的。
-
在单行模式匹配中可以省略括号。[功能 #16182]
[0, 1] => _, x {y: 2} => y: x #=> 1 y #=> 2
-
多重赋值的求值顺序与单重赋值的求值顺序一致。对于单重赋值,Ruby 使用从左到右的求值顺序。使用此代码
foo[0] = bar
使用以下求值顺序
-
foo
-
bar
-
在
foo
的结果上调用[]=
在 Ruby 3.1.0 之前,多重赋值不遵循此求值顺序。使用此代码
foo[0], bar.baz = a, b
Ruby 3.1.0 之前的版本将按以下顺序求值
-
a
-
b
-
foo
-
在
foo
的结果上调用[]=
-
bar
-
在
bar
的结果上调用baz=
从 Ruby 3.1.0 开始,求值顺序现在与单重赋值一致,左侧在右侧之前求值
-
foo
-
bar
-
a
-
b
-
在
foo
的结果上调用[]=
-
在
bar
的结果上调用baz=
[错误 #4443]
-
-
可以省略
Hash
字面量和关键字参数中的值。[功能 #14579]例如,
-
{x:, y:}
是{x: x, y: y}
的语法糖。 -
foo(x:, y:)
是foo(x: x, y: y)
的语法糖。
常量名、局部变量名和方法名允许作为键名。请注意,保留字被视为局部变量或方法名,即使它是伪变量名(如
self
)。 -
-
如果 ivar 引用可共享对象,则非 main-Ractor 可以获取类/模块的实例变量 (ivar)。[功能 #17592]
-
在无尽的方法定义中允许命令语法,例如,你现在可以编写
def foo = puts "Hello"
。请注意,private def foo = puts "Hello"
不会解析。[功能 #17398]
命令行选项¶ ↑
-
--disable-gems
现在被明确声明为“仅用于调试”。永远不要在任何真实世界的代码库中使用它。[功能 #17684]
核心类更新¶ ↑
注意:我们只列出重要的类更新。
-
-
添加了
Array#intersect?
。[功能 #15198]
-
-
-
添加了
Class#subclasses
,它返回直接继承自接收者的类数组,不包括单例类。[功能 #18273]class A; end class B < A; end class C < B; end class D < A; end A.subclasses #=> [D, B] B.subclasses #=> [C] C.subclasses #=> []
-
-
-
添加了
Enumerable#compact
。[功能 #17312] -
Enumerable#tally
现在接受可选的哈希来计数。[功能 #17744] -
Enumerable#each_cons
和 each_slice 现在返回接收器。[GH-1509][1, 2, 3].each_cons(2){} # 3.0 => nil # 3.1 => [1, 2, 3] [1, 2, 3].each_slice(2){} # 3.0 => nil # 3.1 => [1, 2, 3]
-
-
-
File.dirname
现在接受一个可选参数,用于指定要去除路径组件的级别。[功能 #12194]
-
-
-
“GC.measure_total_time = true” 启用
GC
的测量。测量可能会引入开销。默认情况下启用。GC.measure_total_time
返回当前设置。GC.stat[:time]
或GC.stat
(:time) 返回以毫秒为单位的测量时间。[[功能 #10917]] -
GC.total_time
返回以纳秒为单位的测量时间。[[功能 #10917]]
-
-
-
添加了
Integer.try_convert
。[功能 #15211]
-
-
-
Kernel#load
现在接受一个模块作为第二个参数,并且将使用给定的模块作为顶层模块加载文件。[功能 #6210]
-
-
-
Marshal.load
现在接受freeze: true
选项。除Class
和Module
实例之外,所有返回的对象都是冻结的。字符串会被去重。[功能 #18148]
-
-
-
添加了
MatchData#match
。[功能 #18172]
-
-
-
添加了 Method#public?、Method#private?、Method#protected?、UnboundMethod#public?、UnboundMethod#private?、UnboundMethod#protected?。[功能 #11689]
-
-
-
如果接收者已经包含该参数,
Module#prepend
现在会修改祖先链。如果接收者已经预先添加了该参数,Module#prepend
仍然不会修改祖先链。[错误 #17423] -
Module#private
、public、protected 和 module_function 现在将返回它们的参数。如果给出一个参数,则返回该参数。如果没有给出参数,则返回 nil。如果给出多个参数,则将它们作为数组返回。[功能 #12495]
-
-
-
添加了
Process
._fork。这是一个用于 fork(2) 的核心方法。不要直接调用此方法;它由现有的 fork 方法调用:Kernel
.#fork、Process.fork
和IO.popen
(“-”)。应用程序监视库可以覆盖此方法以挂钩 fork 事件。[功能 #17795]
-
-
-
将 Unicode 版本更新到 13.0.0 [功能 #17750],并将 Emoji 版本更新到 13.0 [功能 #18029]
-
String#unpack
和String#unpack1
现在接受一个offset:
关键字参数,以便在跳过任意数量的字节后开始解包。如果offset
超出字符串边界,则会引发ArgumentError
。[功能 #18254]
-
-
-
添加了
Thread::Backtrace.limit
,它返回由--backtrace-limit
命令行选项设置的限制回溯长度的值。[功能 #17479]
-
-
-
Thread::Queue.new
现在接受一个初始值的Enumerable
。[功能 #17327]
-
-
-
Time.new
现在接受可选的in:
时区关键字参数,以及Time.at
和Time.now
,这样你现在可以省略Time.new
的次要参数。[功能 #17485]Time.new(2021, 12, 25, in: "+07:00") #=> 2021-12-25 00:00:00 +0700
同时,时间组件字符串现在会更严格地转换为整数。
Time.new(2021, 12, 25, "+07:30") #=> invalid value for Integer(): "+07:30" (ArgumentError)
Ruby 3.0 或更早版本返回的可能是意想不到的结果
2021-12-25 07:00:00
,而不是2021-12-25 07:30:00
或2021-12-25 00:00:00 +07:30
。 -
Time#strftime
支持 RFC 3339 UTC,对于未知偏移的本地时间,为-0000
,表示为%-z
。[功能 #17544]
-
-
-
添加了
TracePoint.allow_reentry
,以便在TracePoint
回调时允许重新进入。[功能 #15912]
-
-
$LOAD_PATH
-
$LOAD_PATH.resolve_feature_path 不会引发异常。[功能 #16043]
-
-
Fiber
调度器-
添加了使用
address_resolve
钩子的Addrinfo.getaddrinfo
支持。[功能 #17370] -
引入了使用
timeout_after
钩子的非阻塞Timeout.timeout
。[功能 #17470] -
引入新的调度器钩子
io_read
和io_write
,以及用于零拷贝读/写的底层IO::Buffer
。 [特性 #18020] -
IO
钩子io_wait
、io_read
、io_write
在可能的情况下接收原始的IO
对象。 [缺陷 #18003] -
使
Monitor
成为光纤安全的。 [缺陷 #17827] -
用 pthread 实现替换复制协程。 [特性 #18015]
-
-
-
新类,表示由
Module#refine
创建的模块。include
和prepend
已被弃用,并添加了import_methods
代替。 [缺陷 #17429]
-
标准库更新¶ ↑
-
以下默认 gem 已更新。
-
RubyGems 3.3.3
-
base64 0.1.1
-
benchmark 0.2.0
-
bigdecimal 3.1.1
-
bundler 2.3.3
-
cgi 0.3.1
-
csv 3.2.2
-
date 3.2.2
-
did_you_mean 1.6.1
-
digest 3.1.0
-
drb 2.1.0
-
erb 2.2.3
-
error_highlight 0.3.0
-
etc 1.3.0
-
fcntl 1.0.1
-
fiddle 1.1.0
-
fileutils 1.6.0
-
find 0.1.1
-
io-console 0.5.10
-
io-wait 0.2.1
-
ipaddr 1.2.3
-
irb 1.4.1
-
json 2.6.1
-
logger 1.5.0
-
net-http 0.2.0
-
net-protocol 0.1.2
-
nkf 0.1.1
-
open-uri 0.2.0
-
openssl 3.0.0
-
optparse 0.2.0
-
ostruct 0.5.2
-
pathname 0.2.0
-
pp 0.3.0
-
prettyprint 0.1.1
-
psych 4.0.3
-
racc 1.6.0
-
rdoc 6.4.0
-
readline 0.0.3
-
readline-ext 0.1.4
-
reline 0.3.0
-
resolv 0.2.1
-
rinda 0.1.1
-
ruby2_keywords 0.0.5
-
securerandom 0.1.1
-
set 1.0.2
-
stringio 3.0.1
-
strscan 3.0.1
-
tempfile 0.1.2
-
time 0.2.0
-
timeout 0.2.0
-
tmpdir 0.1.2
-
un 0.2.0
-
uri 0.11.0
-
yaml 0.2.0
-
zlib 2.1.1
-
RubyGems 3.3.3
-
base64 0.1.1
-
benchmark 0.2.0
-
bigdecimal 3.1.1
-
bundler 2.3.3
-
cgi 0.3.1
-
csv 3.2.2
-
date 3.2.2
-
did_you_mean 1.6.1
-
digest 3.1.0
-
drb 2.1.0
-
erb 2.2.3
-
error_highlight 0.3.0
-
etc 1.3.0
-
fcntl 1.0.1
-
fiddle 1.1.0
-
fileutils 1.6.0
-
find 0.1.1
-
io-console 0.5.10
-
io-wait 0.2.1
-
ipaddr 1.2.3
-
irb 1.4.1
-
json 2.6.1
-
logger 1.5.0
-
net-http 0.2.0
-
net-protocol 0.1.2
-
nkf 0.1.1
-
open-uri 0.2.0
-
openssl 3.0.0
-
optparse 0.2.0
-
ostruct 0.5.2
-
pathname 0.2.0
-
pp 0.3.0
-
prettyprint 0.1.1
-
psych 4.0.3
-
racc 1.6.0
-
rdoc 6.4.0
-
readline 0.0.3
-
readline-ext 0.1.4
-
reline 0.3.0
-
resolv 0.2.1
-
rinda 0.1.1
-
ruby2_keywords 0.0.5
-
securerandom 0.1.1
-
set 1.0.2
-
stringio 3.0.1
-
strscan 3.0.1
-
tempfile 0.1.2
-
time 0.2.0
-
timeout 0.2.0
-
tmpdir 0.1.2
-
un 0.2.0
-
uri 0.11.0
-
yaml 0.2.0
-
zlib 2.1.1
-
-
以下捆绑的 gem 已更新。
-
minitest 5.15.0
-
power_assert 2.0.1
-
rake 13.0.6
-
test-unit 3.5.3
-
rexml 3.2.5
-
rbs 2.0.0
-
typeprof 0.21.1
-
minitest 5.15.0
-
power_assert 2.0.1
-
rake 13.0.6
-
test-unit 3.5.3
-
rexml 3.2.5
-
rbs 2.0.0
-
typeprof 0.21.1
-
-
以下默认 gem 现在是捆绑的 gem。
-
net-ftp 0.1.3
-
net-imap 0.2.2
-
net-pop 0.1.1
-
net-smtp 0.3.1
-
matrix 0.4.2
-
prime 0.1.2
-
debug 1.4.0
-
net-ftp 0.1.3
-
net-imap 0.2.2
-
net-pop 0.1.1
-
net-smtp 0.3.1
-
matrix 0.4.2
-
prime 0.1.2
-
debug 1.4.0
-
-
以下 gem 已从 Ruby 标准库中删除。
-
dbm
-
gdbm
-
tracer
-
dbm
-
gdbm
-
tracer
-
-
覆盖率测量现在支持暂停。您可以使用
Coverage.suspend
临时停止测量,并使用Coverage.resume
重新启动测量。详见 [特性 #18176]。 -
Random::Formatter
已移至 random/formatter.rb,因此您可以使用Random#hex
、Random#base64
等,而无需 SecureRandom。 [特性 #18190]
兼容性问题¶ ↑
注意:不包括特性缺陷修复。
-
rb_io_wait_readable
、rb_io_wait_writable
和rb_wait_for_single_fd
已被弃用,取而代之的是rb_io_maybe_wait_readable
、rb_io_maybe_wait_writable
和rb_io_maybe_wait
。rb_thread_wait_fd
和rb_thread_fd_writable
已被弃用。 [缺陷 #18003]
标准库兼容性问题¶ ↑
-
即使没有 -w,
ERB#initialize
也会警告safe_level
和后面的参数。 [特性 #14256] -
lib/debug.rb
被debug.gem
替换 -
lib/pp.rb
中的Kernel#pp
默认使用IO#winsize
的宽度。这意味着输出宽度会根据您的终端大小自动更改。 [特性 #12913] -
Psych 4.0 默认将
Psych.load
更改为safe_load
。您可能需要使用 Psych 3.3.2 来迁移到此行为。 [缺陷 #17866]
C API 更新¶ ↑
实现改进¶ ↑
-
引入了用于读取类变量的内联缓存机制。 [特性 #17763]
-
instance_eval
和instance_exec
现在仅在需要时分配单例类,避免了额外的对象并提高了性能。 [GH-5146] -
提高了
Struct
访问器的性能。 [GH-5131] -
mandatory_only?
内置特殊形式,以提高内置方法的性能。 [GH-5112] -
垃圾回收器中的实验性特性可变宽度分配。此特性默认关闭,可以通过使用标志
USE_RVARGC=1
编译 Ruby 来启用。 [特性 #18045] [特性 #18239]
JIT¶ ↑
-
将 Ruby 3.0 的
--jit
重命名为--mjit
,并在非 Windows x86-64 平台上将--jit
别名为--yjit
,在其他平台上别名为--mjit
。
MJIT¶ ↑
-
默认的
--mjit-max-cache
从 100 更改为 10000。 -
当为类事件启用
TracePoint
时,JIT 编译的代码不再被取消。 -
JIT 编译器不再跳过编译长度超过 1000 条指令的方法。
-
当由于使用
TracePoint
或 GC.compact 而禁用 JIT 编译的代码时,--mjit-verbose
和--mjit-warning
输出“JIT cancel”。
YJIT:新的实验性进程内 JIT 编译器¶ ↑
新的 JIT 编译器可用作实验性特性。 [特性 #18229]
请参阅 此博客文章,其中介绍了该项目。
-
默认情况下禁用,使用
--yjit
命令行选项启用 YJIT。 -
基于真实世界软件的基准测试性能改进,railsbench 提升高达 22%,liquid-render 提升高达 39%。
-
快速预热时间。
-
目前仅限于类 Unix x86-64 平台。
静态分析¶ ↑
RBS¶ ↑
-
泛型类型参数可以是有界的(PR)。
# `T` must be compatible with the `_Output` interface. # `PrettyPrint[String]` is ok, but `PrettyPrint[Integer]` is a type error. class PrettyPrint[T < _Output] interface _Output def <<: (String) -> void end attr_reader output: T def initialize: (T output) -> void end
-
类型别名可以是泛型的。(PR)
# Defines a generic type `list`. type list[T] = [ T, list[T] ] | nil type str_list = list[String] type int_list = list[Integer]
-
引入了 rbs 集合来管理 gem 的 RBS。
-
已添加/更新了许多内置和标准库的签名。
-
它还包括许多缺陷修复和性能改进。
有关更多信息,请参阅 CHANGELOG.md。
TypeProf¶ ↑
-
已实现了 实验性 IDE 支持。
-
自 Ruby 3.0.0 以来,进行了许多缺陷修复和性能改进。
调试器¶ ↑
-
捆绑了一个新的调试器 debug.gem。debug.gem 是一个快速的调试器实现,它提供了许多功能,例如远程调试、彩色 REPL、IDE (VSCode) 集成等等。它取代了
lib/debug.rb
标准库。 -
rdbg
命令也安装到bin/
目录中,以启动和控制调试执行。
error_highlight¶ ↑
引入了一个名为 error_highlight 的内置 gem。它在回溯中显示细粒度的错误位置。
示例:title = json[:article][:title]
如果 json
为 nil,则显示
$ ruby test.rb test.rb:2:in `<main>': undefined method `[]' for nil:NilClass (NoMethodError) title = json[:article][:title] ^^^^^^^^^^
如果 json[:article]
返回 nil,则显示
$ ruby test.rb test.rb:2:in `<main>': undefined method `[]' for nil:NilClass (NoMethodError) title = json[:article][:title] ^^^^^^^^
此功能默认启用。您可以使用命令行选项 --disable-error_highlight
禁用它。详见 存储库。
IRB 自动完成和文档显示¶ ↑
IRB 现在具有自动完成功能,您只需键入代码,就会出现完成候选对话框。您可以使用 Tab 和 Shift+Tab 上下移动。
如果在选择完成候选时安装了文档,则文档对话框将出现在完成候选对话框旁边,显示部分内容。您可以按 Alt+d 阅读完整文档。
其他更改¶ ↑
-
添加了 lib/objspace/trace.rb,它是用于跟踪对象分配的工具。只需要求此文件,就会立即开始跟踪。只需使用
Kernel#p
,您就可以调查对象的创建位置。请注意,仅要求此文件会带来很大的性能开销。这仅用于调试目的。请勿在生产环境中使用。 [特性 #17762] -
现在,除非
$VERBOSE
为nil
,否则终结器中引发的异常将打印到STDERR
。 [特性 #17798] -
ruby -run -e httpd
显示用于访问的 URL。 [特性 #17847] -
添加
ruby -run -e colorize
以使用IRB::Color.colorize_code
对 Ruby 代码进行着色。