আমি কীভাবে নেস্টেড হ্যাশ বা ওয়াইএমএল ফাইল থেকে সমস্ত খালি উপাদান (খালি তালিকার আইটেম) সরিয়ে ফেলব?
আমি কীভাবে নেস্টেড হ্যাশ বা ওয়াইএমএল ফাইল থেকে সমস্ত খালি উপাদান (খালি তালিকার আইটেম) সরিয়ে ফেলব?
উত্তর:
আপনি এটির মতো হ্যাশে একটি কমপ্যাক্ট পদ্ধতি যুক্ত করতে পারেন
class Hash
def compact
delete_if { |k, v| v.nil? }
end
end
বা এমন সংস্করণের জন্য যা পুনরাবৃত্তি সমর্থন করে
class Hash
def compact(opts={})
inject({}) do |new_hash, (k,v)|
if !v.nil?
new_hash[k] = opts[:recurse] && v.class == Hash ? v.compact(opts) : v
end
new_hash
end
end
end
Hash#delete_if
এটি একটি ধ্বংসাত্মক অপারেশন, যখন compact
পদ্ধতিগুলি অবজেক্টটিকে সংশোধন করে না। আপনি ব্যবহার করতে পারেন Hash#reject
। অথবা পদ্ধতিটি কল করুন Hash#compact!
।
compact
এবং compact!
রুবি => 2.4.0 আদর্শ আসা, এবং পাগল => 4.1। তারা যদিও পুনরাবৃত্ত হয়।
HashWithIndifferentAccess
.. আমার সংস্করণ পরীক্ষা করুন stackoverflow.com/a/53958201/1519240
৪.১ টি পাখি যোগ করেছে হ্যাশ # কমপ্যাক্ট এবং হ্যাশ # কমপ্যাক্ট! রুবির Hash
ক্লাসে মূল বর্ধন হিসাবে । আপনি তাদের এগুলি ব্যবহার করতে পারেন:
hash = { a: true, b: false, c: nil }
hash.compact
# => { a: true, b: false }
hash
# => { a: true, b: false, c: nil }
hash.compact!
# => { a: true, b: false }
hash
# => { a: true, b: false }
{ c: nil }.compact
# => {}
শিরোনাম: এই প্রয়োগটি পুনরাবৃত্ত হয় না। একটা কৌতুহল আসতেই, তারা এটা ব্যবহার করে বাস্তবায়ন করা #select
পরিবর্তে #delete_if
কর্মক্ষমতা কারণে। মানদণ্ডের জন্য এখানে দেখুন ।
আপনি যদি এটি আপনার রেল 3 অ্যাপে ব্যাকপোর্ট করতে চান তবে:
# config/initializers/rails4_backports.rb
class Hash
# as implemented in Rails 4
# File activesupport/lib/active_support/core_ext/hash/compact.rb, line 8
def compact
self.select { |_, value| !value.nil? }
end
end
Hsh.delete_if ব্যবহার করুন । আপনার নির্দিষ্ট ক্ষেত্রে, এর মতো কিছু:hsh.delete_if { |k, v| v.empty? }
proc = Proc.new { |k, v| v.kind_of?(Hash) ? (v.delete_if(&l); nil) : v.empty? }; hsh.delete_if(&proc)
NoMethodError
হলে একটি নিক্ষেপ করবে v
।
আপনি যদি রুবি ২.৪+ ব্যবহার করেন, আপনি কল করতে পারেন compact
এবংcompact!
h = { a: 1, b: false, c: nil }
h.compact! #=> { a: 1, b: false }
https://ruby-doc.org/core-2.4.0/Hash.html#method-i-compact-21
এটি খালি হ্যাশগুলিও মুছবে:
swoop = Proc.new { |k, v| v.delete_if(&swoop) if v.kind_of?(Hash); v.empty? }
hsh.delete_if &swoop
swoop = Proc.new { |k, v| v.delete_if(&swoop) if v.kind_of?(Hash); v.blank? }
আপনি রুবি হ্যাশ থেকে খালি কী / মান জোড়া সরাতে হ্যাশ # প্রত্যাখ্যান ব্যবহার করতে পারেন ।
# Remove empty strings
{ a: 'first', b: '', c: 'third' }.reject { |key,value| value.empty? }
#=> {:a=>"first", :c=>"third"}
# Remove nil
{a: 'first', b: nil, c: 'third'}.reject { |k,v| v.nil? }
# => {:a=>"first", :c=>"third"}
# Remove nil & empty strings
{a: '', b: nil, c: 'third'}.reject { |k,v| v.nil? || v.empty? }
# => {:c=>"third"}
.empty?
তাই আপনি ব্যবহার করতে পারেন সংখ্যার জন্য ত্রুটি ছোঁড়া, .blank?
এRails
উভয় hashes এবং অ্যারে জন্য কাজ করে
module Helpers
module RecursiveCompact
extend self
def recursive_compact(hash_or_array)
p = proc do |*args|
v = args.last
v.delete_if(&p) if v.respond_to? :delete_if
v.nil? || v.respond_to?(:"empty?") && v.empty?
end
hash_or_array.delete_if(&p)
end
end
end
কারও উত্তর উপর ভিত্তি করে PS, ক্যান্ট খুঁজে
ব্যবহার - Helpers::RecursiveCompact.recursive_compact(something)
আমি জানি এই থ্রেডটি কিছুটা পুরানো তবে আমি আরও ভাল সমাধান নিয়ে এসেছি যা বহুমাত্রিক হ্যাশগুলিকে সমর্থন করে। এটি মুছে ফেলা_আইফ ব্যবহার করে? এর বহুমাত্রিক ব্যতীত এবং ডিফল্টরূপে খালি মান সহ কোনও কিছুই পরিষ্কার করে দেয় এবং যদি কোনও ব্লক পাস হয়ে যায় তবে এটি শিশুদের মধ্য দিয়ে চলে যায়।
# Hash cleaner
class Hash
def clean!
self.delete_if do |key, val|
if block_given?
yield(key,val)
else
# Prepeare the tests
test1 = val.nil?
test2 = val === 0
test3 = val === false
test4 = val.empty? if val.respond_to?('empty?')
test5 = val.strip.empty? if val.is_a?(String) && val.respond_to?('empty?')
# Were any of the tests true
test1 || test2 || test3 || test4 || test5
end
end
self.each do |key, val|
if self[key].is_a?(Hash) && self[key].respond_to?('clean!')
if block_given?
self[key] = self[key].clean!(&Proc.new)
else
self[key] = self[key].clean!
end
end
end
return self
end
end
আমি এর জন্য একটি গভীর_কম্প্যাক্ট পদ্ধতি তৈরি করেছি যা পুনরাবৃত্তভাবে শূন্য রেকর্ডগুলি ফিল্টার করে (এবং optionচ্ছিকভাবে, ফাঁকা রেকর্ডগুলিও):
class Hash
# Recursively filters out nil (or blank - e.g. "" if exclude_blank: true is passed as an option) records from a Hash
def deep_compact(options = {})
inject({}) do |new_hash, (k,v)|
result = options[:exclude_blank] ? v.blank? : v.nil?
if !result
new_value = v.is_a?(Hash) ? v.deep_compact(options).presence : v
new_hash[k] = new_value if new_value
end
new_hash
end
end
end
রুবি Hash#compact
, Hash#compact!
এবং Hash#delete_if!
নেস্টেড nil
, empty?
এবং / অথবা blank?
মানগুলিতে কাজ করে না । মনে রাখবেন যে, আধুনিক দুটি পদ্ধতি ধ্বংসাত্মক হয়, এবং যে সব nil
, ""
, false
, []
এবং {}
মান হিসাবে গণনা করা হয় blank?
।
Hash#compact
এবং Hash#compact!
কেবলমাত্র কারাগারে, বা রুবি সংস্করণে ২.৪.০ এবং তারপরে উপলব্ধ।
এখানে একটি অ-ধ্বংসাত্মক সমাধান যা nil
সমস্ত false
মান রাখার সাথে সাথে সমস্ত খালি অ্যারে, হ্যাশ, স্ট্রিং এবং মানগুলি সরিয়ে দেয় :
( blank?
সাথে nil?
বা empty?
প্রয়োজনের সাথে প্রতিস্থাপন করা যেতে পারে ))
def remove_blank_values(hash)
hash.each_with_object({}) do |(k, v), new_hash|
unless v.blank? && v != false
v.is_a?(Hash) ? new_hash[k] = remove_blank_values(v) : new_hash[k] = v
end
end
end
একটি ধ্বংসাত্মক সংস্করণ:
def remove_blank_values!(hash)
hash.each do |k, v|
if v.blank? && v != false
hash.delete(k)
elsif v.is_a?(Hash)
hash[k] = remove_blank_values!(v)
end
end
end
বা, আপনি যদি Hash
ক্লাসে উদাহরণ পদ্ধতি হিসাবে উভয় সংস্করণ যুক্ত করতে চান :
class Hash
def remove_blank_values
self.each_with_object({}) do |(k, v), new_hash|
unless v.blank? && v != false
v.is_a?(Hash) ? new_hash[k] = v.remove_blank_values : new_hash[k] = v
end
end
end
def remove_blank_values!
self.each_pair do |k, v|
if v.blank? && v != false
self.delete(k)
elsif v.is_a?(Hash)
v.remove_blank_values!
end
end
end
end
অন্যান্য অপশন:
v.blank? && v != false
সাথে প্রতিস্থাপন করুনv.nil? || v == ""
nil
মানগুলিv.blank? && v != false
সঙ্গে v.nil?
কঠোরভাবে মুছে ফেলার জন্য nil
মানfalse
মানগুলি রাখতে এবং অন্যান্য বিকল্পগুলি উপস্থাপন করতে 2017/03/15 সম্পাদনা করুন
হ্যাশে নাল মানগুলি মুছে ফেলার জন্য সাধারণ একটি লাইনারে,
rec_hash.each {|key,value| rec_hash.delete(key) if value.blank? }
blank?
খালি স্ট্রিংয়ের জন্যও যায়
এর মতো ফেসবুক লাইব্রেরি (স্ট্যান্ডার্ড লাইব্রেরি থেকে একটি অনুপস্থিত বৈশিষ্ট্য) দিয়ে করা যেতে পারে :
require 'hash/compact'
require 'enumerable/recursively'
hash.recursively { |v| v.compact! }
যে কোনও গণ্যকারীর সাথে কাজ করে (অ্যারে, হ্যাশ সহ)।
দেখ, আমি কেমন যাও recursively পদ্ধতি বাস্তবায়িত হয়।
আমি বিশ্বাস করি একটি স্ব পুনরাবৃত্তি পদ্ধতি ব্যবহার করা ভাল। যেভাবে এটি প্রয়োজন হিসাবে গভীর হয়। মানটি যদি শূন্য হয় বা খালি হ্যাশ হয় তবে এটি মূল মান জুটি মুছে ফেলবে।
class Hash
def compact
delete_if {|k,v| v.is_a?(Hash) ? v.compact.empty? : v.nil? }
end
end
তারপরে এটি ব্যবহার করা এর মতো দেখতে পাবেন:
x = {:a=>{:b=>2, :c=>3}, :d=>nil, :e=>{:f=>nil}, :g=>{}}
# => {:a=>{:b=>2, :c=>3}, :d=>nil, :e=>{:f=>nil}, :g=>{}}
x.compact
# => {:a=>{:b=>2, :c=>3}}
খালি হ্যাশগুলি রাখতে আপনি এটিকে সহজ করতে পারেন।
class Hash
def compact
delete_if {|k,v| v.compact if v.is_a?(Hash); v.nil? }
end
end
class Hash
def compact
def _empty?(val)
case val
when Hash then val.compact.empty?
when Array then val.all? { |v| _empty?(v) }
when String then val.empty?
when NilClass then true
# ... custom checking
end
end
delete_if { |_key, val| _empty?(val) }
end
end
শূন্যতা অপসারণ করতে এটি চেষ্টা করুন
hash = { a: true, b: false, c: nil }
=> {:a=>true, :b=>false, :c=>nil}
hash.inject({}){|c, (k, v)| c[k] = v unless v.nil?; c}
=> {:a=>true, :b=>false}
hash.compact!
Https://stackoverflow.com/a/14773555/1519240 এর পুনরাবৃত্ত সংস্করণ কাজ করে, তবে এমন HashWithIndifferentAccess
বা অন্যান্য শ্রেণীর সাথে নয় যা হ্যাশ জাতীয় ধরণের ..
আমি যে সংস্করণটি ব্যবহার করছি তা এখানে:
def recursive_compact
inject({}) do |new_hash, (k,v)|
if !v.nil?
new_hash[k] = v.kind_of?(Hash) ? v.recursive_compact : v
end
new_hash
end
end
kind_of?(Hash)
হ্যাশের মতো আরও ক্লাস গ্রহণ করবে।
আপনি চিহ্ন এবং স্ট্রিং উভয়ই ব্যবহার করে নতুন হ্যাশ অ্যাক্সেস করতে চাইলে আপনি এটি inject({})
দ্বারা প্রতিস্থাপন inject(HashWithIndifferentAccess.new)
করতে পারেন।
এখানে আমার কিছু রয়েছে:
# recursively remove empty keys (hashes), values (array), hashes and arrays from hash or array
def sanitize data
case data
when Array
data.delete_if { |value| res = sanitize(value); res.blank? }
when Hash
data.delete_if { |_, value| res = sanitize(value); res.blank? }
end
data.blank? ? nil : data
end
একটি হ্যাশ থেকে গভীর মুছে ফেলা শূন্য।
# returns new instance of hash with deleted nil values
def self.deep_remove_nil_values(hash)
hash.each_with_object({}) do |(k, v), new_hash|
new_hash[k] = deep_remove_nil_values(v) if v.is_a?(Hash)
new_hash[k] = v unless v.nil?
end
end
# rewrite current hash
def self.deep_remove_nil_values!(hash)
hash.each do |k, v|
deep_remove_nil_values(v) if v.is_a?(Hash)
hash.delete(k) if v.nil?
end
end
আপনি যদি সংস্করণ থেকে শুরু করে Rails
(বা স্ট্যান্ডেলোন ActiveSupport
) ব্যবহার করেন 6.1
, এমন একটি compact_blank
পদ্ধতি রয়েছে যা blank
হ্যাশগুলি থেকে মানগুলি সরিয়ে দেয় ।
এটি Object#blank?
কোনও আইটেম ফাঁকা কিনা তা নির্ধারণের জন্য হুডের নীচে ব্যবহার করে ।
{ a: "", b: 1, c: nil, d: [], e: false, f: true }.compact_blank
# => { b: 1, f: true }
এখানে ডক্সের একটি লিঙ্ক এবং আপেক্ষিক PR এর লিঙ্ক ।
একটি ধ্বংসাত্মক রূপটি উপলব্ধ is দেখুন Hash#compact_blank!
।
আপনার যদি প্রয়োজন তবেই সরান nil
মানগুলি ,
দয়া করে, রুবি বিল্ড-ইন Hash#compact
এবং Hash#compact!
পদ্ধতিগুলি বিবেচনা করুন।
{ a: 1, b: false, c: nil }.compact
# => { a: 1, b: false }