2

求人情報を含むテーブルがあります。表示されると、通常は created_at フィールドの降順で並べられます。私は、顧客が自分の求人情報をより多く可視化できるようにする機能を追加する「注目の」ブール値フラグを追加しようとしています。求人の開始から X 日以内の場合、注目のリスティングを検索結果の上部にピン留めしたいと思います。これをサポートするために既存のクエリを変更するにはどうすればよいですか?

Jobs.where("expiration_date >= ? and published = ?", Date.today, true).order("created_at DESC") 

現在のクエリは、created_at 順に並べられた、現在発行されているすべてのジョブを取得します。

4

2 に答える 2

3

他のデータベース (Oracle など) とは異なり、PostgreSQL には完全に機能するbooleanタイプがあります。ステートメントを適用せずに句で直接使用できます。これらは、より複雑な状況に最適です。ORDER BYCASE

boolean値のソート順は次のとおりです。

FALSE -> TRUE -> NULL

場合はORDER BY bool_expressionDESC、次のように順序を逆にします。

NULL -> TRUE -> FALSE

TRUE最初とNULL最後が必要な場合は、次のNULLS LAST句をORDER BY使用します。

ORDER BY (featured AND created_at > now() - interval '11 days') DESC NULLS LAST  
       , created_at DESC

もちろん、はまたはが可能NULLS LASTな場合にのみ関連します。列が定義されている場合は、気にしないでください。featuredcreated_at NULLNOT NULL

また、 のFALSE前にソートされNULLます。これら 2 つを区別したくない場合は、ステートメントに戻るか、またはCASEをスローすることができます。NULLIF()COALESCE()

ORDER BY NULLIF(featured AND created_at > now() - interval '11 days'), FALSE)
                                                                DESC NULLS LAST
       , created_at DESC

パフォーマンス

私がどのように使用したかに注意してください:

created_at > now() - interval '11 days'

はない:

now() - created_at < interval '11 days'

最初の例では、右側の式は1 回計算される定数です。次に、インデックスを使用して、一致する行を検索できます。非常に効率的です。

後者は通常、インデックスでは使用できません。右側の定数式に対して値をチェックする前に、すべての行に対して値を計算する必要があります。回避できる場合は、これを行わないでください。これまで!

于 2012-10-01T21:23:32.620 に答える
0

ここで何を達成したいのかわからない。

結果をページ付けすることになると思います。その場合、ページに関係なく、注目の求人を常に一番上に表示したい場合は、それらを DB から個別にプルする必要があります。最初のページに表示したい場合は、次のpublishedように並べ替えます。

Jobs.where("expiration_date >= ?", Date.today).order("published DESC, created_at DESC") 

それらを別々にプルしたい場合:

@featured_jobs = Jobs.where("expiration_date >= ? and published = ?", Date.today, true).order("created_at DESC")
@regular_jobs = Jobs.where("expiration_date >= ? AND published = ?", Date.today, false).order("created_at DESC") #Paginate them too ... depends on the gem you're using
于 2012-10-01T19:36:36.647 に答える