多个meta_query
与的参数OR
您可以使用
\'relation\' => \'OR\'
中的参数
meta_query
有两套
field_order
参数:一个
meta_value >= \'0\'
另一个是
NOT EXISTS
生成主查询。
\'meta_query\' => array(
\'relation\' => \'OR\',
field_order\' => array(
\'key\' => \'field_order\',
\'value\' => \'0\',
\'compare\' => \'>=\',
\'type\' => \'NUMERIC\'
),
\'field_order_withnulls\' => array(
\'key\' => \'field_order\',
\'compare\' => \'NOT EXISTS\',
\'type\' => \'NUMERIC\'
)
)
我们可以使用
\'field_order_withnulls\' => \'ASC\'
, 但是,由于左连接,将有
null
field_order
值(&A);这些将出现在数字之前
field_order
中的值
ASC
订货人。
为了解决这个问题,我们将使用ORDER BY -field_order DESC
如上所述的技巧here.
这将通过反转来纠正顺序DESC
到ASC
, 但保持与null
数值后的值。
实施-
(反向)运算符输入orderby
问题是,WordPress没有提供任何直接的方法来设置-
(反向)运算符输入orderby
. 因此,我们将引入一个自定义WP_Query
名为的属性_inverse_order
然后使用posts_orderby
筛选以实现它。
示例代码:
// posts_orderby filter callback function
// place this function in theme\'s functions.php file or in a custom plugin
function wpse311227_inverse_orderby( $orderby, $query ) {
remove_filter( \'posts_orderby\', \'wpse311227_inverse_orderby\', 10, 2 );
$idx = (int) $query->get( \'_inverse_order\' ) - 1;
if( $idx >= 0 ) {
$orders = preg_split( "/(?<=ASC|DESC),[\\s]*/i", $orderby );
if( $idx < count( $orders ) ) {
$orders[$idx] = \'-\' . $orders[$idx];
}
return implode( $orders, \', \' );
}
return $orderby;
}
// adding the posts_orderby filter to implement the custom \'_inverse_order\' attribute
// this should be placed just before the WP_Query call
add_filter( \'posts_orderby\', \'wpse311227_inverse_orderby\', 10, 2 );
$args = array(
\'post_type\' => \'insights\',
\'posts_per_page\' => \'9\',
\'meta_query\' => array(
\'relation\' => \'OR\',
field_order\' => array(
\'key\' => \'field_order\',
\'value\' => \'0\',
\'compare\' => \'>=\',
\'type\' => \'NUMERIC\'
),
\'field_order_withnulls\' => array(
\'key\' => \'field_order\',
\'compare\' => \'NOT EXISTS\',
\'type\' => \'NUMERIC\'
)
),
\'orderby\' => array(
\'field_order_withnulls\' => \'DESC\',
\'post_date\' => \'ASC\'
),
// this custom attribute is implemented in wpse311227_inverse_orderby() function
// to correct the ordering by placing a \'-\' operator
// value of _inverse_order attribute is the position of the
// orderby attribute to be be inversed,
// (position starts with 1)
// in this case, since: \'field_order_withnulls\' => \'DESC\'
// is in position 1 of \'orderby\' attribute array, so:
\'_inverse_order\' => 1
);
$query = new WP_Query( $args );
这将生成具有
field_order > 0
还有那些没有
field_order
具有预期顺序的元数据。
Note:您需要传递一个非空value
在里面meta_query
对于NOT EXISTS
检查WordPress版本是否低于3.9。检查此项note from codex:
由于bug#23268,在3.9之前,不存在比较需要值才能正常工作。必须为value参数提供一些字符串。空字符串或NULL无效。但是,任何其他字符串都可以做到这一点,并且在使用NOT EXISTS时不会显示在SQL中。
Warning:此
WP_Query
将使用两个
LEFT JOIN
, 这不是很有效。虽然,即使是几千篇帖子,这也是可以忍受的。我已经测试了15000多篇帖子;查询平均耗时约0.3秒。然而,如果你有数百万甚至数十万篇帖子,那么你必须优化查询或找到更有效的方法来获得相同的结果。