Can someone explain the function of the third parameter of “add_rewrite_tag”

The third parameter tells WordPress what query variable(s) to use/match.

We can query our WordPress database with those public query variables, via requests like example.com/?foo1=bar1&foo2=bar2 but we usually want to rewrite it to something more pretty, like example.com/bar1/bar2/.

In the Codex there’s a list of the default available public query variables:

attachment
attachment_id
author
author_name
cat
category_name
comments_popup
day
error
feed
hour
m
minute
monthnum
name
p
page_id
paged
pagename
post_parent
post_type
preview
second
static
subpost
subpost_id
tag
tag_id
tb
w
year

Example 1:

If we create a custom taxonomy, called for example country, then we will automatically get:

add_rewrite_tag( '%country%', '([^/]+)', 'country=' );

where the third parameter is the query variable that must end with =.

Example 2:

If we want to use the permalink structure example.com/article-1984 for the post post type only, then we can introduce the custom rewrite tag %article-pid%:

add_action( 'init', function(){
    add_rewrite_tag( '%article-pid%', 'article-([0-9]+)', 'p=' );
});

Notice that here the query variable is p and it must end with =.

The request example.com/article-1984 is therefore interpret as example.com/?p=1984, after we flush the rewrite rules, for example by re-saving the permalinks settings.

Then we have to modify the output of the get_permalink() function accordingly:

add_filter( 'post_link', function( $post_link, $post ) {
    return str_replace( '%article-pid%', 'article-' . $post->ID, $post_link );
}, 10, 2 );

Here’s how the permalink settings would look like in this case:

%article-pid%

If we would use article-%post_id% instead, then it seems to mess up the rewrite rules for the other custom post types and taxonomies.