From: blackmoore.joan@... Date: 2016-04-18T05:34:01+00:00 Subject: [ruby-core:74993] [Ruby trunk Bug#11816] Partial safe navigation operator Issue #11816 has been updated by Joan Blackmoore. @Matthew Thought about it again and would agree with the last paragraph. Direct substitution is not appropriate here, despite it sounds logical. The *&.* operator is a strange beast as other general rules also won't apply, like (optional) preceding dot, ie. *object.&.hash* is also a syntax error. Btw. by playing with different &. contained expressions, I've discovered a possible bug: This runs ok `a = nil a&.foo &&= false # nil ` Following however freezes VM and need to be SIGKILLed `nil&.foo &&= false ` Even at bytecode compilation `RubyVM::InstructionSequence.compile('nil&.foo ||= 42') ` tail of strace output lstat("/usr", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0 lstat("/usr/lib64", {st_mode=S_IFDIR|0755, st_size=139264, ...}) = 0 lstat("/usr/lib64/ruby", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0 lstat("/usr/lib64/ruby/2.3.0", {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0 lstat("/usr/lib64/ruby/2.3.0/unicode_normalize.rb", {st_mode=S_IFREG|0644, st_size=3265, ...}) = 0 Tested with `ruby -v ruby 2.3.0p75 (2016-04-07 revision 54505) [x86_64-linux] ` command used `strace ruby --disable=gems,rubyopt -e 'nil&.foo &&= false'` ---------------------------------------- Bug #11816: Partial safe navigation operator https://bugs.ruby-lang.org/issues/11816#change-58120 * Author: Marc-Andre Lafortune * Status: Open * Priority: Normal * Assignee: Yukihiro Matsumoto * ruby -v: preview 2 * Backport: 2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN ---------------------------------------- I'm extremely surprised (and disappointed) that, currently: ```ruby x = nil x&.foo.bar # => NoMethodError: undefined method `bar' for nil:NilClass ``` To make it safe, you have to write `x&.foo&.bar`. But if `foo` is never supposed to return `nil`, then that code isn't "fail early" in case it actually does. `nil&.foo.bar` is more expressive, simpler and is perfect if you want to an error if `foo` returned `nil`. To actually get what you want, you have to resort using the old form `x && x.foo.bar`... In CoffeeScript, you can write `x()?.foo.bar` and it will work well, since it gets compiled to ```js if ((_ref = x()) != null) { _ref.foo.bar; } ``` All the discussion in #11537 focuses on `x&.foo&.bar`, so I have to ask: Matz, what is your understanding of `x&.foo.bar`? I feel the current implementation is not useful and should be changed to what I had in mind. I can't see any legitimate use of `x&.foo.bar` currently. -- https://bugs.ruby-lang.org/ Unsubscribe: