get_categories order by last post

2019-01-29 08:07发布

What is the best and shortest way in Wordpress to get_categories ordered by last posted article?

Means that categories with recent posts should appear first, is it available somehow?

标签: wordpress
2条回答
Evening l夕情丶
2楼-- · 2019-01-29 08:24

Try it:

function get_sorted_categories( $order_by = 'id', $args = array() ){
    global $wpdb;

    $category = get_categories( $args );

    $order = [
        'id' => 'post.ID',
        'date' => 'post.post_date',
        'modified' => 'post.post_modified',
    ];

    $order_by = $order[ $order_by ];

    $q = $wpdb->get_results("SELECT tax.term_id FROM `{$wpdb->prefix}term_taxonomy` tax
    INNER JOIN `{$wpdb->prefix}term_relationships` rel ON rel.term_taxonomy_id = tax.term_id
    INNER JOIN `{$wpdb->prefix}posts` post ON rel.object_id = post.ID WHERE tax.taxonomy = 'category' AND post.post_type = 'post' AND post.post_status = 'publish' ORDER BY {$order_by} DESC");

    $sort = array_flip( array_unique( wp_list_pluck( $q, 'term_id' ) ) );

    usort( $category, function( $a, $b ) use ( $sort, $category ) {
        if( isset( $sort[ $a->term_id ], $sort[ $b->term_id ] ) && $sort[ $a->term_id ] != $sort[ $b->term_id ] )
            $res = ($sort[ $a->term_id ] > $sort[ $b->term_id ]) ? 1 : -1;
        else if( !isset( $sort[ $a->term_id ] ) && isset( $sort[ $b->term_id ] ) )
            $res = 1;
        else if( isset( $sort[ $a->term_id ] ) && !isset( $sort[ $b->term_id ] ) )
            $res = -1;
        else
            $res = 0;

        return $res;
    } );

    return $category;
}

print_r( get_sorted_categories() );
print_r( get_sorted_categories('date') );
print_r( get_sorted_categories('modified') );

Get categories order by (post ID | post date | post modified date). Without any loop and fast!

查看更多
狗以群分
3楼-- · 2019-01-29 08:46

I think the easiest way would be to loop through all of your posts ordered by post_date and then save the categories to an array. You can then loop through the categories and display them. They will be in order.

Something like this:

<?php

// Initiate array
$cats = array();

// Query arguments
$args = array(
    'post_type' => 'post',
    'posts_per_page' => -1,
    'orderby' = 'post_date'.
    'order' => 'DESC'
);

// The query
$query = new WP_Query($args);

// The loop
if($query->have_posts()) {
    while($query->have_posts()) {
        $query->the_post();

        // Get the term object
        $term = get_the_category();

        // Make sure the term doesn't already exist in the array
        if(!array_key_exists($term[0]->ID, $cats)) {
            // Add the terms to the array
            $cats[$term[0]->ID] = $term;
        }
    }
}

foreach($cats as $cid => $cat) {
    // Loop through the categories here
}
?>

Of course, as mentioned in the comment above you could also do it the other way around and loop through the categories first then sort the array. Something like this could do:

<?php

// Initiate array
$cats = get_categories();
$recent_cats = array();

foreach($cats as $k => $cat) {
    // Query arguments
    $args = array(
        'post_type' => 'post',
        'posts_per_page' => 1,
        'orderby' = 'post_date'.
        'order' => 'DESC',
        'cat' => $cat->term_id
    );

    // The query
    $query = new WP_Query($args);

    // The loop
    if($query->have_posts()) {
        while($query->have_posts()) {
            $query->the_post();
            $date_str = strtotime(the_date());
            if(!array_key_exists($date_str, $recent_cats)) {
                $recent_cats[$date_str] = $cat->name;
            }
        }
    }
}

krsort($recent_cats);

// Loop through $recent_cats here

?>
查看更多
登录 后发表回答