R and Python Cheat Sheet

Teaching · IE 3301 Engineering Probability

The same statistics in R and in Python, one line each. Rows marked Watch out are where the two differ in a way that gives a wrong answer without an error. Every row with a number (35 of them) was run in both languages and gives the same result. The worked examples Statistics Basics and Linear Regression and The Basics of Simulation use both languages step by step.

Getting started

TaskRPython
Tools R's statistics are built in; Python's come from three libraries.
# built in: stats, graphics
library(car); library(lmtest)
import numpy as np, pandas as pd
from scipy import stats
import statsmodels.formula.api as smf
Read a whitespace-separated file
df <- read.table("rents.txt", header = TRUE)
df = pd.read_csv("rents.txt", sep=r"\s+")
Column, rows, size
df$Rent; df[1:5, ]; dim(df)
df["Rent"]; df.head(); df.shape
Random seed Watch out: Same seed, different numbers: the two languages use different generators.
set.seed(1)
rng = np.random.default_rng(1)

Describing data

TaskRPython
Mean
mean(x)
np.mean(x)
Sample standard deviation Watch out: numpy's default (ddof=0) divides by n. pandas' .std() divides by n − 1, like R.
sd(x)
np.std(x, ddof=1)
Sample variance
var(x)
np.var(x, ddof=1)
Percentile Both default to the same (linear) rule.
quantile(x, 0.9)
np.quantile(x, 0.9)
Summary
summary(x)
pd.Series(x).describe()
Covariance np.cov divides by n − 1 by default, unlike np.std.
cov(x, y)
np.cov(x, y)[0, 1]
Correlation
cor(x, y)
np.corrcoef(x, y)[0, 1]
Histogram, scatter
hist(x); plot(x, y)
plt.hist(x); plt.scatter(x, y)

Distributions

R names each function by a letter and the distribution: d (density or mass), p (cumulative probability), q (quantile) and r (random draws). SciPy uses methods on the distribution: pdf or pmf, cdf, ppf and rvs.

TaskRPython
Normal density
dnorm(1, mean = 0, sd = 2)
stats.norm.pdf(1, loc=0, scale=2)
P(Z ≤ 1.96)
pnorm(1.96)
stats.norm.cdf(1.96)
P(Z > 1.96)
pnorm(1.96, lower.tail = FALSE)
stats.norm.sf(1.96)
z for 97.5%
qnorm(0.975)
stats.norm.ppf(0.975)
Five normal draws
rnorm(5, mean = 10, sd = 2)
rng.normal(10, 2, size=5)
Binomial P(X = 3) Watch out: Discrete distributions have pmf, not pdf, in SciPy.
dbinom(3, size = 10, prob = 0.2)
stats.binom.pmf(3, 10, 0.2)
Binomial P(X ≤ 3)
pbinom(3, size = 10, prob = 0.2)
stats.binom.cdf(3, 10, 0.2)
Poisson P(X = 2), mean 3
dpois(2, lambda = 3)
stats.poisson.pmf(2, 3)
Exponential P(X ≤ 2), rate 0.5 Watch out: SciPy takes the mean (scale = 1/rate), not the rate.
pexp(2, rate = 0.5)
stats.expon.cdf(2, scale=1/0.5)
Gamma P(X ≤ 3), shape 2, rate 0.5 Watch out: Shape is a; again scale = 1/rate.
pgamma(3, shape = 2, rate = 0.5)
stats.gamma.cdf(3, a=2, scale=1/0.5)
Uniform on [0, 2]: P(X ≤ 0.3) Watch out: SciPy's scale is the width, not the maximum.
punif(0.3, min = 0, max = 2)
stats.uniform.cdf(0.3, loc=0, scale=2)
t for 97.5%, 9 df
qt(0.975, df = 9)
stats.t.ppf(0.975, df=9)
Chi-square 95th percentile, 4 df
qchisq(0.95, df = 4)
stats.chi2.ppf(0.95, 4)
F 95th percentile, 3 and 20 df
qf(0.95, 3, 20)
stats.f.ppf(0.95, 3, 20)

Intervals and tests

TaskRPython
One-sample t test
t.test(x, mu = 5)
stats.ttest_1samp(x, 5)
95% CI for the mean R prints it with every t test.
t.test(x)$conf.int
stats.ttest_1samp(x, 0).confidence_interval()
Two-sample t test Watch out: R defaults to Welch's test; SciPy pools the variances unless equal_var=False.
t.test(x, y)
stats.ttest_ind(x, y, equal_var=False)
Paired t test
t.test(x, y, paired = TRUE)
stats.ttest_rel(x, y)
F test of two variances No one-line SciPy version.
var.test(x, y)
F = np.var(x, ddof=1) / np.var(y, ddof=1)
p = 2 * min(stats.f.cdf(F, 9, 9), stats.f.sf(F, 9, 9))
Test of one proportion Watch out: From statsmodels; R matches it only with correct = FALSE.
prop.test(45, 100, p = 0.5, correct = FALSE)
proportions_ztest(45, 100, 0.5, prop_var=0.5)
Chi-square test of independence
chisq.test(tab)
stats.chi2_contingency(tab)
Shapiro-Wilk normality test
shapiro.test(x)
stats.shapiro(x)

Regression

TaskRPython
Fit y on x The same formula language in both.
fit <- lm(y ~ x, data = df)
fit = smf.ols("y ~ x", data=df).fit()
Coefficients
coef(fit)
fit.params
Full table
summary(fit)
fit.summary()
R²
summary(fit)$r.squared
fit.rsquared
CIs for the coefficients
confint(fit)
fit.conf_int()
Confidence interval for the mean at x = 5 Columns mean_ci_lower, mean_ci_upper.
predict(fit, new, interval = "confidence")
fit.get_prediction(new).summary_frame()
Prediction interval at x = 5 Columns obs_ci_lower, obs_ci_upper.
predict(fit, new, interval = "prediction")
fit.get_prediction(new).summary_frame()
Residual plots R draws four diagnostic plots at once.
plot(fit)
sm.qqplot(fit.resid, line="s")
plt.scatter(fit.fittedvalues, fit.resid)
Variance inflation factors Watch out: car in R. Python needs the design matrix, intercept included; skip column 0.
vif(fit2)
X = fit2.model.exog
[variance_inflation_factor(X, j) for j in (1, 2)]
Breusch-Pagan test From lmtest in R. Both default to the studentized (Koenker) form.
bptest(fit)
het_breuschpagan(fit.resid, fit.model.exog)
One-way ANOVA Wrap a text column in C() in Python to treat it as categories.
summary(aov(y ~ g, data = df))
sm.stats.anova_lm(smf.ols("y ~ C(g)", data=df).fit())

Simulation

TaskRPython
Roll a die ten times Watch out: Python's upper bound is excluded: 7, not 6.
sample(1:6, 10, replace = TRUE)
rng.integers(1, 7, size=10)
1,000 means of 5 exponentials Python draws a whole table at once and averages each row.
replicate(1000, mean(rexp(5, rate = 1)))
rng.exponential(1, size=(1000, 5)).mean(axis=1)

Python here means numpy, pandas, SciPy and statsmodels (pip install numpy pandas scipy statsmodels matplotlib); R needs only install.packages(c("car", "lmtest")) beyond what it ships with. Free in the browser: Google Colab for Python and Posit Cloud for R.