List all posts by year with pagination

Here is my approach. What I interpreted and accepted is that you need to display the year on each and every first post on each page, and also you only need to display the year on subsequent posts if the year is different than that of the first year.

I did not want to use extra function which made extra db calls, also I tried to use the post objects which are available through the $wp_query global. This is what I came up with

STEP 1

Get the date in year form from the current post in the loop. I have used get_the_date() here.

STEP 2

You need to get the post date from the previous post, except when the current post is not the first post. To do this, you need to access the $wp_query->posts array, and get the post_date object from the previous WP_Post object. To get that, I’ve used the $wp_query->current_post counter, subtracted one and used that as the array key to access the array.

STEP 3

Covert the post_date with mysql2date to get the year in which the previous post was published.

STEP 4

If the current post is the first post, display the year the post was published in. If the current post is not the first post, you need to compare the current post’s year with the year from the previous post. If these values match, the date should not be printed, and when these values don’t match, print the date

ALL TOGETHER NOW!!

You can now put this code together, and display it inside the loop where you need to display it

$current_year = get_the_date('Y');

if( 0 != $wp_query->current_post ) {        
    $f = $wp_query->current_post - 1;       
    $old_date =   mysql2date( 'Y', $wp_query->posts[$f]->post_date ); 

    if($current_year != $old_date) {
        echo $current_year;
    }
}else{
    echo $current_year;
}

EDIT

To remove the date from all first posts from subsequent pages if the year match the last post from the previous page, you can do the following

$current_year = get_the_date('Y');

if( 0 != $wp_query->current_post ) {        
    $f = $wp_query->current_post - 1;       
    $old_date = mysql2date( 'Y', $wp_query->posts[$f]->post_date ); 

    if($current_year != $old_date) {
        echo $current_year;
    }
}elseif( is_paged() && 0 == $wp_query->current_post ) {
    $old_date =   get_the_date( 'Y', get_next_post()->ID );

    if($current_year != $old_date) {
        echo $current_year;
    }
}else{
    echo $current_year;
}