Published on
November 12, 2021
Updated on
April 28, 2022
‣
Candidates
The table below shows the 12 candidates to the French 2022 Presidential Election. Column Polls was their latest 7-day rolling average score before Election Day for the 1st round. Spectrum gives an indication of where the party is on the political spectrum, from far-left to far-right.
Candidate | 1st round last polls | 1st round result | Political party | Spectrum |
Emmanuel MACRON | 26.5% | 27.85% | The Republic On The Move | ···•··· |
Marine LE PEN | 22.4% | 23.15% | National Rally | ·····•· |
Jean-Luc MÉLENCHON | 16.5% | 21.95% | France Unbowed | ·•····· |
Éric ZEMMOUR | 9.4% | 7.07% | Reconquest | ······• |
Valérie PÉCRESSE | 9.0% | 4.78% | The Republicans | ····•·· |
Yannick JADOT | 5.2% | 4.63% | Europe Ecology The Greens | ·•····· |
Jean LASSALLE | 2.9% | 3.13% | Resist | ···•··· |
Fabien ROUSSEL | 2.5% | 2.28% | French Communist Party | ·•····· |
Nicolas DUPONT-AIGNAN | 2.0% | 2.06% | Stand Up France | ·····•· |
Anne HIDALGO | 2.1% | 1.75% | Socialist Party | ··•···· |
Philippe POUTOU | 1.0% | 0.77% | New Anticapitalist Party | •······ |
Nathalie ARTHAUD | 0.5% | 0.56% | Workers Struggle | •······ |
Polls for Second Round
Emmanuel Macron and Marine Le Pen have been qualified for the second round of the presidential election on 24th April 2022. The plots show their moving averages over 3 days, with a 95% confidence interval.
super-embed:
<iframe src="https://storage.googleapis.com/charlse/charlse/tour2.html" height="520"><iframe>
‣
# Plotly graph for Macron vs Le Pen
### Format plot
fig = go.Figure(
layout=go.Layout(
template='simple_white',
height=500, width=740,
margin=dict(l=15, r=25, b=15,t=40),
xaxis_range=['2022-01-01', '2022-04-24'],
yaxis_range=[0.3, 0.7],
yaxis_tickformat='.0%',
yaxis_tickfont=dict(size=11, family='Arial'),
xaxis_tickfont=dict(size=11, family='Arial'),
legend=dict(yanchor='top', y=1, xanchor='left', x=0, orientation='h'),
hovermode='x unified',
)
)
### Plot line
fig.add_trace(go.Scatter(
x=df_mean_tour2.loc[lambda x: x['candidat'] == 'Macron', 'date'],
y=df_mean_tour2.loc[lambda x: x['candidat'] == 'Macron', 'rol_avg'],
hovertemplate='<extra>{}</extra>%{}'.format('Macron', '{y:.1%}'),
mode='lines',
line_color=candidates_colors['Macron'],
name='Macron')
)
fig.add_trace(go.Scatter(
x=df_mean_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'date'],
y=df_mean_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'rol_avg'],
hovertemplate='<extra>{}</extra>%{}'.format('Le Pen', '{y:.1%}'),
mode='lines',
line_color=candidates_colors['Le Pen'],
name='Le Pen')
)
### Confidence intervals
fig.add_trace(go.Scatter(
x=df_mean_tour2.loc[lambda x: x['candidat'] == 'Macron', 'date'],
y=df_mean_tour2.loc[lambda x: x['candidat'] == 'Macron', 'rol_ci_low'],
hoverinfo='skip', showlegend=False,
mode='lines',
line=dict(color=candidates_colors['Macron'], width=0)),
)
fig.add_trace(go.Scatter(
x=df_mean_tour2.loc[lambda x: x['candidat'] == 'Macron', 'date'],
y=df_mean_tour2.loc[lambda x: x['candidat'] == 'Macron', 'rol_ci_hi'],
hoverinfo='skip', showlegend=False,
mode='lines',
fill='tonexty',
line=dict(color=candidates_colors['Macron'], width=0)),
)
fig.add_trace(go.Scatter(
x=df_mean_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'date'],
y=df_mean_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'rol_ci_low'],
hoverinfo='skip', showlegend=False,
mode='lines',
line=dict(color=candidates_colors['Le Pen'], width=0)),
)
fig.add_trace(go.Scatter(
x=df_mean_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'date'],
y=df_mean_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'rol_ci_hi'],
hoverinfo='skip', showlegend=False,
mode='lines',
fill='tonexty',
opacity=.1,
line=dict(color=candidates_colors['Le Pen'], width=0)),
)
### Plot scatter
fig.add_trace(go.Scatter(
x=df_tour2.loc[lambda x: x['candidat'] == 'Macron', 'date'],
y=df_tour2.loc[lambda x: x['candidat'] == 'Macron', 'value'],
hoverinfo='skip', showlegend=False,
mode='markers', opacity=.3,
line_color=candidates_colors['Macron']),
)
fig.add_trace(go.Scatter(
x=df_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'date'],
y=df_tour2.loc[lambda x: x['candidat'] == 'Le Pen', 'value'],
hoverinfo='skip', showlegend=False,
mode='markers', opacity=.3,
line_color=candidates_colors['Le Pen']),
)
### Horizontal dotted line at 50%
fig.add_shape(
type='line',
y0=.5, y1=.5,
x0='2022-01-01', x1='2022-04-24',
line=dict(color='black', width=1, dash='dot')
)
## Display result
fig.show()
Polls for First Round
The graph below aggregates opinion polls for the first round of the election on 10th April 2022, released by the main french polling organizations. Each dot represents a poll result for a candidate, and dots radius is proportional to polls sample size.
super-embed:
<iframe src="https://storage.googleapis.com/charlse/charlse/tour1.html"height="520"><iframe>
‣
# Plotly graph
## Candidates to display
candidates_colors = {
'Barnier': 'royalblue',
'Bertrand': 'deepskyblue',
'Hidalgo': 'lightcoral',
'Jadot': 'green',
'Le Pen': 'saddlebrown',
'Macron': 'orange',
'Mélenchon': 'firebrick',
'Pécresse': 'steelblue',
'Roussel': 'palevioletred',
'Zemmour': 'black'
}
selected_candidates = sorted(['Macron', 'Le Pen', 'Pécresse',
'Jadot', 'Zemmour', 'Hidalgo', 'Mélenchon', 'Roussel'])
## Line plot
fig1 = px.line(
df_mean.loc[lambda x: x['candidat'].isin(selected_candidates)],
x='date', y='rol_avg', color='candidat',
color_discrete_map=candidates_colors
)
fig1.update_traces(hovertemplate='%{y:.1%}', line=dict(width=2.5), showlegend=True)
## Scatter graph
fig2 = px.scatter(
df_polls.loc[lambda x: x['candidat'].isin(selected_candidates)],
x='date', y='value', color='candidat', opacity=.2,
size='norm_sample', size_max=12,
color_discrete_map=candidates_colors
)
fig2.update_traces(hovertemplate=None, hoverinfo='skip', showlegend=False)
## Display both plots
fig3 = go.Figure(
data=fig2.data + fig1.data,
layout=go.Layout(
template='simple_white',
height=500, width=740,
margin=dict(l=5, r=5, b=5,t=5),
xaxis_range=['2021-08-15', '2022-04-10'],
yaxis_range=[0., .40],
yaxis_tickformat='.0%',
yaxis_tickfont=dict(size=11, family='Arial'),
xaxis_tickfont=dict(size=11, family='Arial'),
legend=dict(yanchor='top', y=1, xanchor='left', x=0, orientation='h')
)
)
fig3.show()
Sources
- NSP Polls for polls list
- FiveThirtyEight for inspiration