4

この行に次のコードがあります。

user.attributes.except('created_at', 'created_by', 'updated_at', 'updated_by', 'id')

動作します(引数として渡されたキーが削除されたハッシュを返します)が、次のように変更します。

user.attributes.except(:created_at, :created_by, :updated_at, :updated_by, :id)

ありません(返されたハッシュにはまだすべてのキーが含まれています)。これはどのように可能ですか?

4

4 に答える 4

8

属性は、キーをシンボルではなく文字列として持つハッシュを返すためです。

http://apidock.com/rails/ActiveRecord/Base/attributes

そして他の人が言ったように、String!=Symbol。

puts :a == 'a'
# => false
于 2012-08-16T08:18:10.483 に答える
7

これは、のキーuser.attributesが文字列であるために発生します。symbolize_keysメソッドを使用してそれらをシンボル化し、次にexceptこのようなシンボルで使用できます。

user.attributes.symbolize_keys.except(:created_at, :created_by, :updated_at, :updated_by, :id)
于 2012-08-16T08:18:29.763 に答える
0

場合によってはこの動作を望まない(http json応答の処理など)

そこで、改良を加えました。

module HashUtil
  refine Hash do
    def eager_except(*args)
      proc = Proc.new do |key|
        case
          when key.is_a?(Symbol)
            key.to_s
          when key.is_a?(String)
            key.to_sym
          else
            nil
        end
      end
      eager_args = (args + args.map(&proc)).compact
      except(*eager_args)
    end
  end
end


using HashUtil
hash = { a: 'a', "b" => 'b' }
hash.eager_except('a', :b)
# => {}

※ 追加情報

上に書いた後、私は他の方法を見つけました。

すべてのキーをHash#deep_symbolize_keysでシンボルに変換します!

{"a" => "hoge"}.deep_symbolize_keys!.except(:a) # => {}

ActiveSupport::HashWithIndifferentAccessを使用する

{"a" => "hoge"}.with_indifferent_access.except(:a) # => {}

ありがとう

于 2018-02-14T08:31:02.550 に答える
0

Ruby 3はHash#exceptを追加して、指定されたキーとその値を除くハッシュを返します。

irb(main):001:0> user_details = { name: 'Akhil', age: 25, address: 'India', password: 'T:%g6R' }

irb(main):002:0> puts user_details.except(:password)
=> { name: 'Akhil', age: 25, address: 'India' }
于 2020-11-14T17:56:22.000 に答える