2011-07-20 10 views
2

Array/SetのようなオブジェクトまたはHash型の引数を受け入れるメソッドがあります。型チェックを避けながら配列型または集合型の値を検出する方法

def find(query = {}) 
    if Array === query or Set === query 
    query = {:_id => {'$in' => query.to_a}} 
    end 
    mongo_collection.find(query) 
end 

方法IDオブジェクトのセットを受け入れ、MongoDBのためのハッシュ条件にそれを向けるだろう。この方法の要点は次のようなものです。上記のコードで

2つの問題:

  1. 「設定」が標準ライブラリから必要とされていない場合、それは失敗します。私はチェックを実行するだけで依存関係を要求したくありません。
  2. 私は厳密な型比較をしたくありません。私は任意の配列またはセットのような値を受け入れ、to_aで値の配列にキャストしたいと思います。

このチェックはどのように実行しますか?心の中で持っているいくつかの注意事項:

  1. 私はto_ary方法をチェックすることもできますが、設定はto_aryに応答しません。このメソッドを実装するオブジェクトは基本的に配列でなければならず、私はSetが基本的に配列ではないことに同意します。私は行くことにしました

    [:&, :+, :-, :<<, :collect!, :flatten!, :map!, :|] 
    

Consequences of implementing to_int and to_str in Ruby

  • 私はハッシュがそれに配列し、設定するために共通している
  • 方法を応答しますので、to_aをチェックすることはできませんが、ハッシュしないようである参照してください。

    これは、集合体のようなオブジェクトが交差する可能性が高いためです。しかし、私はこれについては分かりません。

  • +0

    基本的にあなたはダックタイピングについて話しています。配列のように動作することができるなら、オブジェクトが何であるかは気にしません。したがって、オブジェクトに '.to_a'を追加し、配列に変換できるかどうかを確認してください。ハッシュが必要な場合は、配列に変換してハッシュを作成したいと思うでしょう: 'Hash [* array.to_a.flatten]'。その時点で、適切なクラスを要求するのは発信者の仕事です。 –

    答えて

    1

    どのように考えていますか?

    def find(query = {}) 
        query = {:_id => {'$in' => query.to_a}} unless query.respond_to?(:has_key?) 
        mongo_collection.find(query) 
    end 
    

    has_keyに応答すると、オブジェクトはハッシュまたはハッシュのようになることが予想されます。

    +1

    これは、この具体的な問題の最も洗練された解決策ですが、オリジナルの一般的な質問には答えません。 "配列や設定値を検出する方法"。しかたがない – mislav

    0

    Setが定義されているかどうかを確認すると、最初の問題が解決されます。 2番目の方法では、クエリのクラスの先祖を調べて、Arrayがその中にあるかどうかを調べることができますが、おそらくすべての「配列のような」オブジェクトを捕捉することはできません。おそらく、配列をテストするメソッドの存在をチェックしないでしょう。名前をテストするのであって、動作ではないからです。 Arelは特に&に応答します(または非難された前にしました)が、このタイプのオブジェクトはあなたが望むように動作しません。

    if not Hash === query and query.respond_to? :to_a 
    

    私はちょうどto_aをチェックするよ、私は、だけでなく、それはハッシュオブジェクトではないことを確実にすることに興味がある唯一の方法である:

    4

    は、ここに私のテイクです。私は厳密な型チェックをハッシュに使用していますが、これは根本的にハッシュである完全に別のクラスとして渡される可能性が最も低いオブジェクトであるためです。

    0

    個人的に私は、クエリのようなハッシュであるかどうかを確認しようとしているについて...

    def find(query = {})  
        mongo_collection.find(query_formatter(query)) 
    end 
    
    def query_formatter(query) 
        if query.respond_to?(:to_a) && !query.kind_of?(Hash) 
        {:_id => {'$in' => query.to_a}} 
        else 
        query 
        end 
    end 
    
    関連する問題