Tools

Practice Datasets

Reading about a t-test is not the same as running one. These eight small, realistic CSV files each come with a story, three suggested exercises, and a worked solution with the real numbers, so you can practice every analysis on data that behaves like the messy, interesting real thing.

How to use them: download a CSV, open it in SPSS, JASP, R, Python, or even the Descriptives calculator right here, and try the exercises. Peek at the worked solution only after you've had a go. The numbers there are computed from the exact file you downloaded, so they'll match if you did it right.

Every file is generated by a seeded, committed script (tools/make-datasets.py, master seed 20260709). Rerunning it reproduces byte-for-byte identical CSVs, so the shipped worked-solution numbers stay true. Nothing here is uploaded anywhere; the files are static.

😴Sleep & attention

⬇ sleep-experiment.csv · 80 rows

Eighty volunteers were randomly assigned to a normal night's sleep or a night restricted to four hours, then took a 30-minute vigilance task the next morning. The outcome is the number of attention lapses (errors). Did sleep restriction hurt performance, and by how much?

VariableTypeDescription
participant_idID1–80, one row per person
conditioncategoricalnormal_sleep vs restricted_sleep (40 each)
errorscountattention lapses on the vigilance task

Try these

  1. Run an independent-samples t-test comparing errors across the two conditions.
  2. Report and interpret Cohen's d: the study was built around a medium effect (check it with the effect-size converter).
  3. Before trusting the p-value, check the assumptions (normality, equal variances).
Worked solution: the key numbers
  • normal_sleep: M = 20.07, SD = 5.92, n = 40
  • restricted_sleep: M = 22.77, SD = 6.02, n = 40
  • Independent t-test: t(78) = 2.02, p = .047
  • Effect size: d = 0.45, a medium effect. Restricted sleepers made more errors.

Three groups of 35 students revised for the same exam using one of three techniques (rereading, flashcards, or practice testing), then sat the exam (scored 0–100). Which method wins? And notice the spread differs by group, so this doubles as a homogeneity-of-variance workout.

VariableTypeDescription
student_idID1–105, one row per student
methodcategoricalrereading · flashcards · practice_testing
exam_scorecontinuousfinal exam mark, 0–100

Try these

  1. Run a one-way ANOVA across the three methods.
  2. Check equal variances (Levene's test). The SDs are deliberately unequal.
  3. Follow up with post-hoc tests (e.g. Tukey) to see which methods actually differ.
Worked solution: the key numbers
  • rereading: M = 66.14, SD = 7.97 · flashcards: M = 74.43, SD = 8.86 · practice_testing: M = 76.83, SD = 11.97
  • SD ratio (largest / smallest) = 1.50, enough heterogeneity for Levene to notice.
  • One-way ANOVA: F(2, 102) = 11.57, p < .001, η² = .185.
  • Practice testing > flashcards > rereading; post-hoc, rereading is the one that clearly trails.

📱Screen time & sleep

⬇ screen-time.csv · 60 rows

Sixty people reported their average daily screen time and rated their sleep quality (0–10). There's a real negative relationship in here, but one person (row 60) reports 11.5 hours of screen time and excellent sleep, sitting far off to the right. This dataset is really about what one influential point can do.

VariableTypeDescription
person_idID1–60, one row per person
screen_hourscontinuousaverage screen time per day (hours)
sleep_qualitycontinuousself-rated sleep quality, 0–10

Try these

  1. Plot it, then compute Pearson's r. Always look before you trust a coefficient.
  2. Fit a simple regression and inspect leverage & influence (Cook's distance) for row 60.
  3. Recompute r without that point, then decide what to do with it, and report both.
Worked solution: the key numbers
  • All 60 points: r = −.21 (slope = −0.23), which looks weak.
  • Drop the influential person 60 (11.5 h, 8.6): r = −.40 (slope = −0.56) — the real, moderate relationship.
  • A single high-leverage point moved r by .19 and nearly halved the slope.
  • Honest line (without the point): sleep ≈ 7.92 − 0.56 × screen_hours.

A classic 2×2 memory experiment: participants encoded a word list either shallowly or deeply, then were tested in the same room or a different one (25 per cell). The number of words recalled hides a genuine interaction: context only matters when encoding was deep.

VariableTypeDescription
idID1–100, one row per participant
encodingcategoricalshallow vs deep
contextcategoricalsame vs different room at test
recallcountwords recalled (0–30)

Try these

  1. Run a two-way factorial ANOVA. You want the encoding × context interaction.
  2. Draw the interaction plot of the four cell means (non-parallel lines = interaction).
  3. Put the interaction into words: the effect of context depends on encoding depth.
Worked solution: the key numbers
  • Cell means: shallow/same = 9.32, shallow/different = 8.20; deep/same = 19.04, deep/different = 14.12.
  • Context effect when shallow = 1.12 words; when deep = 4.92 words.
  • Interaction (difference of those differences) ≈ 3.80 words, so the lines are clearly non-parallel.
  • Main effect of encoding is large; context alone is small — the story lives in the interaction.

An 8-item wellbeing questionnaire (each item 1–5). Two items are negatively worded and must be reverse-coded before scoring: q3 and q6. A few cells are blank (real surveys have missing data). Practice reverse-coding, building a composite, and checking the scale's reliability.

VariableTypeDescription
respondent_idID1–120, one row per respondent
q1 … q8ordinal (Likert)1–5 agreement; q3 & q6 reverse-worded; blank = missing

Try these

  1. Reverse-code q3 and q6 (new = 6 − old), then compute a composite (mean of the 8 items).
  2. Assess the scale with Cronbach's α.
  3. Decide how to handle the missing values (listwise vs pairwise) and note how many cases each keeps.
Worked solution: the key numbers
  • Reverse-code q3 and q6 as 6 − x before anything else, or α will look terrible.
  • 51 cells are missing; listwise deletion leaves 75 of 120 complete cases (a real cost: pairwise keeps more).
  • Cronbach's α (raw, complete cases) = .90, a reliable scale.
  • Composite score: M = 2.88, SD = 0.93.

🩺Messy clinic intake

⬇ messy-clinic.csv · 52 rows

A deliberately dirty clinic intake sheet, built for the Data course. It hides duplicates, impossible values, a unit mix-up, inconsistent category spellings, and three different date formats. Your job is to find every problem before you analyze anything, and to never edit the raw file, only a cleaning script.

VariableTypeDescription
patient_idIDP001–P050 (with two duplicated rows)
agecountyears (one value is impossible)
sexcategoricaleight different spellings of two categories
height_cmcontinuouscm (one row is in meters, another impossible)
weight_kgcontinuouskg (one is negative)
systolic_bpcountmmHg (one is zero)
visit_datedatethree inconsistent formats

Try these

  1. Find and document every data-quality problem. How many can you spot before reading the solution?
  2. Build a reproducible cleaning workflow: de-duplicate, standardize sex, fix the units, parse the dates.
  3. Write the validation rules (allowed ranges, allowed categories) that would have caught each error at entry.
Worked solution: the planted problems
  • Duplicates: P004 is an exact duplicate row; P016 appears twice with a slightly different weight (near-duplicate).
  • Impossible values: age 511 (P007, a typo for 51), systolic_bp 0 (P020), weight −78 kg (P031, a sign error), height 400 cm (P042).
  • Unit mix-up: P013's height is 1.72 — that's meters, not cm.
  • Inconsistent categories: sex is spelled eight ways: Male/M/male/ Male  vs Female/F/female/f/  female (mind the whitespace).
  • Date formats: mostly ISO (2025-06-08), but 07/04/2025 (P034) and April 12 2025 (P039) sneak in.
  • After cleaning: 50 unique patients remain (two duplicate rows removed); the impossible values are then fixed or flagged, not silently deleted.

🏋️Strength training

⬇ training-longitudinal.csv · 60 rows

Sixty athletes were measured on a strength lift (1RM, kg) at weeks 0, 6, and 12, split between a training program and a control group. The data is in wide format (one row per athlete, one column per timepoint), perfect for practicing reshaping and repeated-measures analysis.

VariableTypeDescription
athlete_idID1–60, one row per athlete
groupcategoricalprogram vs control (30 each)
strength_wk0continuousbaseline 1RM (kg)
strength_wk6continuous1RM at week 6 (kg)
strength_wk12continuous1RM at week 12 (kg)

Try these

  1. Pivot wide → long so each row is one athlete-at-one-time (R/JASP usually want long).
  2. Run a repeated-measures / mixed ANOVA with time (within) and group (between).
  3. Interpret the group × time interaction: does the program gain more than the control?
Worked solution: the key numbers
  • Program means (wk0 / wk6 / wk12): 101.5 / 107.7 / 110.2 kg, a gain of about +8.7 kg.
  • Control means (wk0 / wk6 / wk12): 101.9 / 103.8 / 105.1 kg, a gain of about +3.2 kg.
  • Both improve over time, but the program improves more → a group × time interaction.
  • After pivoting, you'll have 180 rows (60 athletes × 3 timepoints).

🎓Grad admissions

⬇ admissions.csv · 160 rows

Records for 160 graduate applicants: undergraduate GPA, a GRE-style test score, whether they had research experience, and the binary outcome: admitted or not. A binary outcome means logistic regression, not linear.

VariableTypeDescription
applicant_idIDA001–A160, one row per applicant
gpacontinuousundergraduate GPA, 2.0–4.0
gre_scorecountstandardized test score (~260–340)
researchbinary1 = has research experience, 0 = none
admittedbinary1 = admitted, 0 = rejected (the outcome)

Try these

  1. Fit a logistic regression: admitted ~ gpa + gre_score + research.
  2. Interpret the odds ratios (convert them from the coefficients; the effect-size tool handles OR too).
  3. As a warm-up, compare admit rates by research with a chi-square test on the 2×2 table.
Worked solution: the key numbers
  • Overall admit rate = 45.6% (73 of 160).
  • Admit rate: research = 58.0% vs no research = 36.3%, so research helps.
  • Mean GPA: admitted = 3.44 vs rejected = 3.16.
  • Logistic fit: GPA b = 3.98 (OR ≈ 53.6 per whole GPA point), GRE b = 0.029, research b = 1.37 (OR ≈ 3.9). All three predictors point the right way.

Got your own numbers instead? Paste them into the Descriptives calculator for a full rundown, size your next study with the Power calculator, or format the result with the APA formatter.