{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# First steps with DataFrames.jl\n",
"\n",
"### Bogumił Kamiński\n",
"\n",
"In this notebook we will reproduce the classical Anscombe's quartert plot.\n",
"\n",
"Our objective is to produce a figure similar to this one (the plot is taken from https://upload.wikimedia.org/wikipedia/commons/e/ec/Anscombe%27s_quartet_3.svg):"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"![Anscombe's quartet](https://upload.wikimedia.org/wikipedia/commons/e/ec/Anscombe%27s_quartet_3.svg)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We start with loading of the required packages"
]
},
{
"cell_type": "code",
"execution_count": 1,
"metadata": {},
"outputs": [],
"source": [
"using DataFrames"
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {},
"outputs": [],
"source": [
"using Statistics"
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {},
"outputs": [],
"source": [
"using PyPlot"
]
},
{
"cell_type": "code",
"execution_count": 4,
"metadata": {},
"outputs": [],
"source": [
"using GLM"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"This is a matrix in which we store 8 columns representing Anscombe's quartet data"
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11×8 Array{Float64,2}:\n",
" 10.0 8.04 10.0 9.14 10.0 7.46 8.0 6.58\n",
" 8.0 6.95 8.0 8.14 8.0 6.77 8.0 5.76\n",
" 13.0 7.58 13.0 8.74 13.0 12.74 8.0 7.71\n",
" 9.0 8.81 9.0 8.77 9.0 7.11 8.0 8.84\n",
" 11.0 8.33 11.0 9.26 11.0 7.81 8.0 8.47\n",
" 14.0 9.96 14.0 8.1 14.0 8.84 8.0 7.04\n",
" 6.0 7.24 6.0 6.13 6.0 6.08 8.0 5.25\n",
" 4.0 4.26 4.0 3.1 4.0 5.39 19.0 12.5\n",
" 12.0 10.84 12.0 9.13 12.0 8.15 8.0 5.56\n",
" 7.0 4.82 7.0 7.26 7.0 6.42 8.0 7.91\n",
" 5.0 5.68 5.0 4.74 5.0 5.73 8.0 6.89"
]
},
"execution_count": 5,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"aq = [10.0 8.04 10.0 9.14 10.0 7.46 8.0 6.58\n",
" 8.0 6.95 8.0 8.14 8.0 6.77 8.0 5.76\n",
" 13.0 7.58 13.0 8.74 13.0 12.74 8.0 7.71\n",
" 9.0 8.81 9.0 8.77 9.0 7.11 8.0 8.84\n",
" 11.0 8.33 11.0 9.26 11.0 7.81 8.0 8.47\n",
" 14.0 9.96 14.0 8.1 14.0 8.84 8.0 7.04\n",
" 6.0 7.24 6.0 6.13 6.0 6.08 8.0 5.25\n",
" 4.0 4.26 4.0 3.1 4.0 5.39 19.0 12.50 \n",
" 12.0 10.84 12.0 9.13 12.0 8.15 8.0 5.56\n",
" 7.0 4.82 7.0 7.26 7.0 6.42 8.0 7.91\n",
" 5.0 5.68 5.0 4.74 5.0 5.73 8.0 6.89]"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We can simply convert a maxtrx to a `DataFrame` by calling its constructor"
]
},
{
"cell_type": "code",
"execution_count": 6,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"
x1 x2 x3 x4 x5 x6 x7 x8 Float64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 11 rows × 8 columns
1 10.0 8.04 10.0 9.14 10.0 7.46 8.0 6.58 2 8.0 6.95 8.0 8.14 8.0 6.77 8.0 5.76 3 13.0 7.58 13.0 8.74 13.0 12.74 8.0 7.71 4 9.0 8.81 9.0 8.77 9.0 7.11 8.0 8.84 5 11.0 8.33 11.0 9.26 11.0 7.81 8.0 8.47 6 14.0 9.96 14.0 8.1 14.0 8.84 8.0 7.04 7 6.0 7.24 6.0 6.13 6.0 6.08 8.0 5.25 8 4.0 4.26 4.0 3.1 4.0 5.39 19.0 12.5 9 12.0 10.84 12.0 9.13 12.0 8.15 8.0 5.56 10 7.0 4.82 7.0 7.26 7.0 6.42 8.0 7.91 11 5.0 5.68 5.0 4.74 5.0 5.73 8.0 6.89
"
],
"text/latex": [
"\\begin{tabular}{r|cccccccc}\n",
"\t& x1 & x2 & x3 & x4 & x5 & x6 & x7 & x8\\\\\n",
"\t\\hline\n",
"\t& Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64\\\\\n",
"\t\\hline\n",
"\t1 & 10.0 & 8.04 & 10.0 & 9.14 & 10.0 & 7.46 & 8.0 & 6.58 \\\\\n",
"\t2 & 8.0 & 6.95 & 8.0 & 8.14 & 8.0 & 6.77 & 8.0 & 5.76 \\\\\n",
"\t3 & 13.0 & 7.58 & 13.0 & 8.74 & 13.0 & 12.74 & 8.0 & 7.71 \\\\\n",
"\t4 & 9.0 & 8.81 & 9.0 & 8.77 & 9.0 & 7.11 & 8.0 & 8.84 \\\\\n",
"\t5 & 11.0 & 8.33 & 11.0 & 9.26 & 11.0 & 7.81 & 8.0 & 8.47 \\\\\n",
"\t6 & 14.0 & 9.96 & 14.0 & 8.1 & 14.0 & 8.84 & 8.0 & 7.04 \\\\\n",
"\t7 & 6.0 & 7.24 & 6.0 & 6.13 & 6.0 & 6.08 & 8.0 & 5.25 \\\\\n",
"\t8 & 4.0 & 4.26 & 4.0 & 3.1 & 4.0 & 5.39 & 19.0 & 12.5 \\\\\n",
"\t9 & 12.0 & 10.84 & 12.0 & 9.13 & 12.0 & 8.15 & 8.0 & 5.56 \\\\\n",
"\t10 & 7.0 & 4.82 & 7.0 & 7.26 & 7.0 & 6.42 & 8.0 & 7.91 \\\\\n",
"\t11 & 5.0 & 5.68 & 5.0 & 4.74 & 5.0 & 5.73 & 8.0 & 6.89 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"11×8 DataFrame. Omitted printing of 1 columns\n",
"│ Row │ x1 │ x2 │ x3 │ x4 │ x5 │ x6 │ x7 │\n",
"│ │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤\n",
"│ 1 │ 10.0 │ 8.04 │ 10.0 │ 9.14 │ 10.0 │ 7.46 │ 8.0 │\n",
"│ 2 │ 8.0 │ 6.95 │ 8.0 │ 8.14 │ 8.0 │ 6.77 │ 8.0 │\n",
"│ 3 │ 13.0 │ 7.58 │ 13.0 │ 8.74 │ 13.0 │ 12.74 │ 8.0 │\n",
"│ 4 │ 9.0 │ 8.81 │ 9.0 │ 8.77 │ 9.0 │ 7.11 │ 8.0 │\n",
"│ 5 │ 11.0 │ 8.33 │ 11.0 │ 9.26 │ 11.0 │ 7.81 │ 8.0 │\n",
"│ 6 │ 14.0 │ 9.96 │ 14.0 │ 8.1 │ 14.0 │ 8.84 │ 8.0 │\n",
"│ 7 │ 6.0 │ 7.24 │ 6.0 │ 6.13 │ 6.0 │ 6.08 │ 8.0 │\n",
"│ 8 │ 4.0 │ 4.26 │ 4.0 │ 3.1 │ 4.0 │ 5.39 │ 19.0 │\n",
"│ 9 │ 12.0 │ 10.84 │ 12.0 │ 9.13 │ 12.0 │ 8.15 │ 8.0 │\n",
"│ 10 │ 7.0 │ 4.82 │ 7.0 │ 7.26 │ 7.0 │ 6.42 │ 8.0 │\n",
"│ 11 │ 5.0 │ 5.68 │ 5.0 │ 4.74 │ 5.0 │ 5.73 │ 8.0 │"
]
},
"execution_count": 6,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"df = DataFrame(aq)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Note that the auto-generated column names are `x1`, `x2`, etc."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Next we replace automatically generated column names by proper ones."
]
},
{
"cell_type": "code",
"execution_count": 7,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"8-element Array{String,1}:\n",
" \"x1\"\n",
" \"y1\"\n",
" \"x2\"\n",
" \"y2\"\n",
" \"x3\"\n",
" \"y3\"\n",
" \"x4\"\n",
" \"y4\""
]
},
"execution_count": 7,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"newnames = vec(string.([\"x\", \"y\"], [1 2 3 4]))"
]
},
{
"cell_type": "code",
"execution_count": 8,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"x1 y1 x2 y2 x3 y3 x4 y4 Float64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 11 rows × 8 columns
1 10.0 8.04 10.0 9.14 10.0 7.46 8.0 6.58 2 8.0 6.95 8.0 8.14 8.0 6.77 8.0 5.76 3 13.0 7.58 13.0 8.74 13.0 12.74 8.0 7.71 4 9.0 8.81 9.0 8.77 9.0 7.11 8.0 8.84 5 11.0 8.33 11.0 9.26 11.0 7.81 8.0 8.47 6 14.0 9.96 14.0 8.1 14.0 8.84 8.0 7.04 7 6.0 7.24 6.0 6.13 6.0 6.08 8.0 5.25 8 4.0 4.26 4.0 3.1 4.0 5.39 19.0 12.5 9 12.0 10.84 12.0 9.13 12.0 8.15 8.0 5.56 10 7.0 4.82 7.0 7.26 7.0 6.42 8.0 7.91 11 5.0 5.68 5.0 4.74 5.0 5.73 8.0 6.89
"
],
"text/latex": [
"\\begin{tabular}{r|cccccccc}\n",
"\t& x1 & y1 & x2 & y2 & x3 & y3 & x4 & y4\\\\\n",
"\t\\hline\n",
"\t& Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64\\\\\n",
"\t\\hline\n",
"\t1 & 10.0 & 8.04 & 10.0 & 9.14 & 10.0 & 7.46 & 8.0 & 6.58 \\\\\n",
"\t2 & 8.0 & 6.95 & 8.0 & 8.14 & 8.0 & 6.77 & 8.0 & 5.76 \\\\\n",
"\t3 & 13.0 & 7.58 & 13.0 & 8.74 & 13.0 & 12.74 & 8.0 & 7.71 \\\\\n",
"\t4 & 9.0 & 8.81 & 9.0 & 8.77 & 9.0 & 7.11 & 8.0 & 8.84 \\\\\n",
"\t5 & 11.0 & 8.33 & 11.0 & 9.26 & 11.0 & 7.81 & 8.0 & 8.47 \\\\\n",
"\t6 & 14.0 & 9.96 & 14.0 & 8.1 & 14.0 & 8.84 & 8.0 & 7.04 \\\\\n",
"\t7 & 6.0 & 7.24 & 6.0 & 6.13 & 6.0 & 6.08 & 8.0 & 5.25 \\\\\n",
"\t8 & 4.0 & 4.26 & 4.0 & 3.1 & 4.0 & 5.39 & 19.0 & 12.5 \\\\\n",
"\t9 & 12.0 & 10.84 & 12.0 & 9.13 & 12.0 & 8.15 & 8.0 & 5.56 \\\\\n",
"\t10 & 7.0 & 4.82 & 7.0 & 7.26 & 7.0 & 6.42 & 8.0 & 7.91 \\\\\n",
"\t11 & 5.0 & 5.68 & 5.0 & 4.74 & 5.0 & 5.73 & 8.0 & 6.89 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"11×8 DataFrame. Omitted printing of 1 columns\n",
"│ Row │ x1 │ y1 │ x2 │ y2 │ x3 │ y3 │ x4 │\n",
"│ │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤\n",
"│ 1 │ 10.0 │ 8.04 │ 10.0 │ 9.14 │ 10.0 │ 7.46 │ 8.0 │\n",
"│ 2 │ 8.0 │ 6.95 │ 8.0 │ 8.14 │ 8.0 │ 6.77 │ 8.0 │\n",
"│ 3 │ 13.0 │ 7.58 │ 13.0 │ 8.74 │ 13.0 │ 12.74 │ 8.0 │\n",
"│ 4 │ 9.0 │ 8.81 │ 9.0 │ 8.77 │ 9.0 │ 7.11 │ 8.0 │\n",
"│ 5 │ 11.0 │ 8.33 │ 11.0 │ 9.26 │ 11.0 │ 7.81 │ 8.0 │\n",
"│ 6 │ 14.0 │ 9.96 │ 14.0 │ 8.1 │ 14.0 │ 8.84 │ 8.0 │\n",
"│ 7 │ 6.0 │ 7.24 │ 6.0 │ 6.13 │ 6.0 │ 6.08 │ 8.0 │\n",
"│ 8 │ 4.0 │ 4.26 │ 4.0 │ 3.1 │ 4.0 │ 5.39 │ 19.0 │\n",
"│ 9 │ 12.0 │ 10.84 │ 12.0 │ 9.13 │ 12.0 │ 8.15 │ 8.0 │\n",
"│ 10 │ 7.0 │ 4.82 │ 7.0 │ 7.26 │ 7.0 │ 6.42 │ 8.0 │\n",
"│ 11 │ 5.0 │ 5.68 │ 5.0 │ 4.74 │ 5.0 │ 5.73 │ 8.0 │"
]
},
"execution_count": 8,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"rename!(df, newnames)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We could have also assigned the names to columns at the moment of data frame creation like this:"
]
},
{
"cell_type": "code",
"execution_count": 9,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"x1 y1 x2 y2 x3 y3 x4 y4 Float64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 11 rows × 8 columns
1 10.0 8.04 10.0 9.14 10.0 7.46 8.0 6.58 2 8.0 6.95 8.0 8.14 8.0 6.77 8.0 5.76 3 13.0 7.58 13.0 8.74 13.0 12.74 8.0 7.71 4 9.0 8.81 9.0 8.77 9.0 7.11 8.0 8.84 5 11.0 8.33 11.0 9.26 11.0 7.81 8.0 8.47 6 14.0 9.96 14.0 8.1 14.0 8.84 8.0 7.04 7 6.0 7.24 6.0 6.13 6.0 6.08 8.0 5.25 8 4.0 4.26 4.0 3.1 4.0 5.39 19.0 12.5 9 12.0 10.84 12.0 9.13 12.0 8.15 8.0 5.56 10 7.0 4.82 7.0 7.26 7.0 6.42 8.0 7.91 11 5.0 5.68 5.0 4.74 5.0 5.73 8.0 6.89
"
],
"text/latex": [
"\\begin{tabular}{r|cccccccc}\n",
"\t& x1 & y1 & x2 & y2 & x3 & y3 & x4 & y4\\\\\n",
"\t\\hline\n",
"\t& Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64\\\\\n",
"\t\\hline\n",
"\t1 & 10.0 & 8.04 & 10.0 & 9.14 & 10.0 & 7.46 & 8.0 & 6.58 \\\\\n",
"\t2 & 8.0 & 6.95 & 8.0 & 8.14 & 8.0 & 6.77 & 8.0 & 5.76 \\\\\n",
"\t3 & 13.0 & 7.58 & 13.0 & 8.74 & 13.0 & 12.74 & 8.0 & 7.71 \\\\\n",
"\t4 & 9.0 & 8.81 & 9.0 & 8.77 & 9.0 & 7.11 & 8.0 & 8.84 \\\\\n",
"\t5 & 11.0 & 8.33 & 11.0 & 9.26 & 11.0 & 7.81 & 8.0 & 8.47 \\\\\n",
"\t6 & 14.0 & 9.96 & 14.0 & 8.1 & 14.0 & 8.84 & 8.0 & 7.04 \\\\\n",
"\t7 & 6.0 & 7.24 & 6.0 & 6.13 & 6.0 & 6.08 & 8.0 & 5.25 \\\\\n",
"\t8 & 4.0 & 4.26 & 4.0 & 3.1 & 4.0 & 5.39 & 19.0 & 12.5 \\\\\n",
"\t9 & 12.0 & 10.84 & 12.0 & 9.13 & 12.0 & 8.15 & 8.0 & 5.56 \\\\\n",
"\t10 & 7.0 & 4.82 & 7.0 & 7.26 & 7.0 & 6.42 & 8.0 & 7.91 \\\\\n",
"\t11 & 5.0 & 5.68 & 5.0 & 4.74 & 5.0 & 5.73 & 8.0 & 6.89 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"11×8 DataFrame. Omitted printing of 1 columns\n",
"│ Row │ x1 │ y1 │ x2 │ y2 │ x3 │ y3 │ x4 │\n",
"│ │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤\n",
"│ 1 │ 10.0 │ 8.04 │ 10.0 │ 9.14 │ 10.0 │ 7.46 │ 8.0 │\n",
"│ 2 │ 8.0 │ 6.95 │ 8.0 │ 8.14 │ 8.0 │ 6.77 │ 8.0 │\n",
"│ 3 │ 13.0 │ 7.58 │ 13.0 │ 8.74 │ 13.0 │ 12.74 │ 8.0 │\n",
"│ 4 │ 9.0 │ 8.81 │ 9.0 │ 8.77 │ 9.0 │ 7.11 │ 8.0 │\n",
"│ 5 │ 11.0 │ 8.33 │ 11.0 │ 9.26 │ 11.0 │ 7.81 │ 8.0 │\n",
"│ 6 │ 14.0 │ 9.96 │ 14.0 │ 8.1 │ 14.0 │ 8.84 │ 8.0 │\n",
"│ 7 │ 6.0 │ 7.24 │ 6.0 │ 6.13 │ 6.0 │ 6.08 │ 8.0 │\n",
"│ 8 │ 4.0 │ 4.26 │ 4.0 │ 3.1 │ 4.0 │ 5.39 │ 19.0 │\n",
"│ 9 │ 12.0 │ 10.84 │ 12.0 │ 9.13 │ 12.0 │ 8.15 │ 8.0 │\n",
"│ 10 │ 7.0 │ 4.82 │ 7.0 │ 7.26 │ 7.0 │ 6.42 │ 8.0 │\n",
"│ 11 │ 5.0 │ 5.68 │ 5.0 │ 4.74 │ 5.0 │ 5.73 │ 8.0 │"
]
},
"execution_count": 9,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"DataFrame(aq, [:x1, :y1, :x2, :y2, :x3, :y3, :x4, :y4])"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"> You might have noticed that in the first example we used a string (e.g. `\"x1\"`) as column name and in the second one we used a `Symbol` (e.g. `:x1`). This was intentional. DataFrames.jl allows you to use either of them for column indexing.\n",
"\n",
"To see the above rule at work let us extract the second column `:y1` from this data frame. Here are several options how you can do it:"
]
},
{
"cell_type": "code",
"execution_count": 10,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11-element Array{Float64,1}:\n",
" 8.04\n",
" 6.95\n",
" 7.58\n",
" 8.81\n",
" 8.33\n",
" 9.96\n",
" 7.24\n",
" 4.26\n",
" 10.84\n",
" 4.82\n",
" 5.68"
]
},
"execution_count": 10,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"df.y1"
]
},
{
"cell_type": "code",
"execution_count": 11,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11-element Array{Float64,1}:\n",
" 8.04\n",
" 6.95\n",
" 7.58\n",
" 8.81\n",
" 8.33\n",
" 9.96\n",
" 7.24\n",
" 4.26\n",
" 10.84\n",
" 4.82\n",
" 5.68"
]
},
"execution_count": 11,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"df.\"y1\""
]
},
{
"cell_type": "code",
"execution_count": 12,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11-element Array{Float64,1}:\n",
" 8.04\n",
" 6.95\n",
" 7.58\n",
" 8.81\n",
" 8.33\n",
" 9.96\n",
" 7.24\n",
" 4.26\n",
" 10.84\n",
" 4.82\n",
" 5.68"
]
},
"execution_count": 12,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"df[:, :y1]"
]
},
{
"cell_type": "code",
"execution_count": 13,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11-element Array{Float64,1}:\n",
" 8.04\n",
" 6.95\n",
" 7.58\n",
" 8.81\n",
" 8.33\n",
" 9.96\n",
" 7.24\n",
" 4.26\n",
" 10.84\n",
" 4.82\n",
" 5.68"
]
},
"execution_count": 13,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"df[:, \"y1\"]"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Assume that now we want to reorder columns of the data frame `df` in-place by first grouping the \"x\"-columns and then \"y\" columns.\n",
"\n",
"This can be easiliy achieved with the `select!` function.\n",
"\n",
"Note that in column selection we can in particular use regular expressions like `r\"x\"` (matching all columns that have `\"x\"` in their name) and `:` which matches all columns (in this case only columns not having `\"x\"` in ther name are left)"
]
},
{
"cell_type": "code",
"execution_count": 14,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"x1 x2 x3 x4 y1 y2 y3 y4 Float64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 11 rows × 8 columns
1 10.0 10.0 10.0 8.0 8.04 9.14 7.46 6.58 2 8.0 8.0 8.0 8.0 6.95 8.14 6.77 5.76 3 13.0 13.0 13.0 8.0 7.58 8.74 12.74 7.71 4 9.0 9.0 9.0 8.0 8.81 8.77 7.11 8.84 5 11.0 11.0 11.0 8.0 8.33 9.26 7.81 8.47 6 14.0 14.0 14.0 8.0 9.96 8.1 8.84 7.04 7 6.0 6.0 6.0 8.0 7.24 6.13 6.08 5.25 8 4.0 4.0 4.0 19.0 4.26 3.1 5.39 12.5 9 12.0 12.0 12.0 8.0 10.84 9.13 8.15 5.56 10 7.0 7.0 7.0 8.0 4.82 7.26 6.42 7.91 11 5.0 5.0 5.0 8.0 5.68 4.74 5.73 6.89
"
],
"text/latex": [
"\\begin{tabular}{r|cccccccc}\n",
"\t& x1 & x2 & x3 & x4 & y1 & y2 & y3 & y4\\\\\n",
"\t\\hline\n",
"\t& Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64\\\\\n",
"\t\\hline\n",
"\t1 & 10.0 & 10.0 & 10.0 & 8.0 & 8.04 & 9.14 & 7.46 & 6.58 \\\\\n",
"\t2 & 8.0 & 8.0 & 8.0 & 8.0 & 6.95 & 8.14 & 6.77 & 5.76 \\\\\n",
"\t3 & 13.0 & 13.0 & 13.0 & 8.0 & 7.58 & 8.74 & 12.74 & 7.71 \\\\\n",
"\t4 & 9.0 & 9.0 & 9.0 & 8.0 & 8.81 & 8.77 & 7.11 & 8.84 \\\\\n",
"\t5 & 11.0 & 11.0 & 11.0 & 8.0 & 8.33 & 9.26 & 7.81 & 8.47 \\\\\n",
"\t6 & 14.0 & 14.0 & 14.0 & 8.0 & 9.96 & 8.1 & 8.84 & 7.04 \\\\\n",
"\t7 & 6.0 & 6.0 & 6.0 & 8.0 & 7.24 & 6.13 & 6.08 & 5.25 \\\\\n",
"\t8 & 4.0 & 4.0 & 4.0 & 19.0 & 4.26 & 3.1 & 5.39 & 12.5 \\\\\n",
"\t9 & 12.0 & 12.0 & 12.0 & 8.0 & 10.84 & 9.13 & 8.15 & 5.56 \\\\\n",
"\t10 & 7.0 & 7.0 & 7.0 & 8.0 & 4.82 & 7.26 & 6.42 & 7.91 \\\\\n",
"\t11 & 5.0 & 5.0 & 5.0 & 8.0 & 5.68 & 4.74 & 5.73 & 6.89 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"11×8 DataFrame. Omitted printing of 1 columns\n",
"│ Row │ x1 │ x2 │ x3 │ x4 │ y1 │ y2 │ y3 │\n",
"│ │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤\n",
"│ 1 │ 10.0 │ 10.0 │ 10.0 │ 8.0 │ 8.04 │ 9.14 │ 7.46 │\n",
"│ 2 │ 8.0 │ 8.0 │ 8.0 │ 8.0 │ 6.95 │ 8.14 │ 6.77 │\n",
"│ 3 │ 13.0 │ 13.0 │ 13.0 │ 8.0 │ 7.58 │ 8.74 │ 12.74 │\n",
"│ 4 │ 9.0 │ 9.0 │ 9.0 │ 8.0 │ 8.81 │ 8.77 │ 7.11 │\n",
"│ 5 │ 11.0 │ 11.0 │ 11.0 │ 8.0 │ 8.33 │ 9.26 │ 7.81 │\n",
"│ 6 │ 14.0 │ 14.0 │ 14.0 │ 8.0 │ 9.96 │ 8.1 │ 8.84 │\n",
"│ 7 │ 6.0 │ 6.0 │ 6.0 │ 8.0 │ 7.24 │ 6.13 │ 6.08 │\n",
"│ 8 │ 4.0 │ 4.0 │ 4.0 │ 19.0 │ 4.26 │ 3.1 │ 5.39 │\n",
"│ 9 │ 12.0 │ 12.0 │ 12.0 │ 8.0 │ 10.84 │ 9.13 │ 8.15 │\n",
"│ 10 │ 7.0 │ 7.0 │ 7.0 │ 8.0 │ 4.82 │ 7.26 │ 6.42 │\n",
"│ 11 │ 5.0 │ 5.0 │ 5.0 │ 8.0 │ 5.68 │ 4.74 │ 5.73 │"
]
},
"execution_count": 14,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"select!(df, r\"x\", :)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Note that we could have used `select` instead of `select!` function to create a new data frame (instead of mutating the data frame in question in-place)."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"An interesting feature of Anscombe's quartet is that its variables have the same mean and variance.\n",
"\n",
"We can easily check this using the `describe` function."
]
},
{
"cell_type": "code",
"execution_count": 15,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"variable mean std Symbol Float64 Float64 8 rows × 3 columns
1 x1 9.0 3.31662 2 x2 9.0 3.31662 3 x3 9.0 3.31662 4 x4 9.0 3.31662 5 y1 7.50091 2.03157 6 y2 7.50091 2.03166 7 y3 7.5 2.03042 8 y4 7.50091 2.03058
"
],
"text/latex": [
"\\begin{tabular}{r|ccc}\n",
"\t& variable & mean & std\\\\\n",
"\t\\hline\n",
"\t& Symbol & Float64 & Float64\\\\\n",
"\t\\hline\n",
"\t1 & x1 & 9.0 & 3.31662 \\\\\n",
"\t2 & x2 & 9.0 & 3.31662 \\\\\n",
"\t3 & x3 & 9.0 & 3.31662 \\\\\n",
"\t4 & x4 & 9.0 & 3.31662 \\\\\n",
"\t5 & y1 & 7.50091 & 2.03157 \\\\\n",
"\t6 & y2 & 7.50091 & 2.03166 \\\\\n",
"\t7 & y3 & 7.5 & 2.03042 \\\\\n",
"\t8 & y4 & 7.50091 & 2.03058 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"8×3 DataFrame\n",
"│ Row │ variable │ mean │ std │\n",
"│ │ \u001b[90mSymbol\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼──────────┼─────────┼─────────┤\n",
"│ 1 │ x1 │ 9.0 │ 3.31662 │\n",
"│ 2 │ x2 │ 9.0 │ 3.31662 │\n",
"│ 3 │ x3 │ 9.0 │ 3.31662 │\n",
"│ 4 │ x4 │ 9.0 │ 3.31662 │\n",
"│ 5 │ y1 │ 7.50091 │ 2.03157 │\n",
"│ 6 │ y2 │ 7.50091 │ 2.03166 │\n",
"│ 7 │ y3 │ 7.5 │ 2.03042 │\n",
"│ 8 │ y4 │ 7.50091 │ 2.03058 │"
]
},
"execution_count": 15,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"describe(df, :mean => mean, :std => std)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Just to practice the string/`Symbol` duality let us write the same using strings for column names:"
]
},
{
"cell_type": "code",
"execution_count": 16,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"variable mean std Symbol Float64 Float64 8 rows × 3 columns
1 x1 9.0 3.31662 2 x2 9.0 3.31662 3 x3 9.0 3.31662 4 x4 9.0 3.31662 5 y1 7.50091 2.03157 6 y2 7.50091 2.03166 7 y3 7.5 2.03042 8 y4 7.50091 2.03058
"
],
"text/latex": [
"\\begin{tabular}{r|ccc}\n",
"\t& variable & mean & std\\\\\n",
"\t\\hline\n",
"\t& Symbol & Float64 & Float64\\\\\n",
"\t\\hline\n",
"\t1 & x1 & 9.0 & 3.31662 \\\\\n",
"\t2 & x2 & 9.0 & 3.31662 \\\\\n",
"\t3 & x3 & 9.0 & 3.31662 \\\\\n",
"\t4 & x4 & 9.0 & 3.31662 \\\\\n",
"\t5 & y1 & 7.50091 & 2.03157 \\\\\n",
"\t6 & y2 & 7.50091 & 2.03166 \\\\\n",
"\t7 & y3 & 7.5 & 2.03042 \\\\\n",
"\t8 & y4 & 7.50091 & 2.03058 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"8×3 DataFrame\n",
"│ Row │ variable │ mean │ std │\n",
"│ │ \u001b[90mSymbol\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼──────────┼─────────┼─────────┤\n",
"│ 1 │ x1 │ 9.0 │ 3.31662 │\n",
"│ 2 │ x2 │ 9.0 │ 3.31662 │\n",
"│ 3 │ x3 │ 9.0 │ 3.31662 │\n",
"│ 4 │ x4 │ 9.0 │ 3.31662 │\n",
"│ 5 │ y1 │ 7.50091 │ 2.03157 │\n",
"│ 6 │ y2 │ 7.50091 │ 2.03166 │\n",
"│ 7 │ y3 │ 7.5 │ 2.03042 │\n",
"│ 8 │ y4 │ 7.50091 │ 2.03058 │"
]
},
"execution_count": 16,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"describe(df, \"mean\" => mean, \"std\" => std)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Now let us add a new column `id` to the data frame that will just index its rows form 1 to number of rows."
]
},
{
"cell_type": "code",
"execution_count": 17,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"x1 x2 x3 x4 y1 y2 y3 y4 id Float64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 Int64 11 rows × 9 columns
1 10.0 10.0 10.0 8.0 8.04 9.14 7.46 6.58 1 2 8.0 8.0 8.0 8.0 6.95 8.14 6.77 5.76 2 3 13.0 13.0 13.0 8.0 7.58 8.74 12.74 7.71 3 4 9.0 9.0 9.0 8.0 8.81 8.77 7.11 8.84 4 5 11.0 11.0 11.0 8.0 8.33 9.26 7.81 8.47 5 6 14.0 14.0 14.0 8.0 9.96 8.1 8.84 7.04 6 7 6.0 6.0 6.0 8.0 7.24 6.13 6.08 5.25 7 8 4.0 4.0 4.0 19.0 4.26 3.1 5.39 12.5 8 9 12.0 12.0 12.0 8.0 10.84 9.13 8.15 5.56 9 10 7.0 7.0 7.0 8.0 4.82 7.26 6.42 7.91 10 11 5.0 5.0 5.0 8.0 5.68 4.74 5.73 6.89 11
"
],
"text/latex": [
"\\begin{tabular}{r|ccccccccc}\n",
"\t& x1 & x2 & x3 & x4 & y1 & y2 & y3 & y4 & id\\\\\n",
"\t\\hline\n",
"\t& Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Int64\\\\\n",
"\t\\hline\n",
"\t1 & 10.0 & 10.0 & 10.0 & 8.0 & 8.04 & 9.14 & 7.46 & 6.58 & 1 \\\\\n",
"\t2 & 8.0 & 8.0 & 8.0 & 8.0 & 6.95 & 8.14 & 6.77 & 5.76 & 2 \\\\\n",
"\t3 & 13.0 & 13.0 & 13.0 & 8.0 & 7.58 & 8.74 & 12.74 & 7.71 & 3 \\\\\n",
"\t4 & 9.0 & 9.0 & 9.0 & 8.0 & 8.81 & 8.77 & 7.11 & 8.84 & 4 \\\\\n",
"\t5 & 11.0 & 11.0 & 11.0 & 8.0 & 8.33 & 9.26 & 7.81 & 8.47 & 5 \\\\\n",
"\t6 & 14.0 & 14.0 & 14.0 & 8.0 & 9.96 & 8.1 & 8.84 & 7.04 & 6 \\\\\n",
"\t7 & 6.0 & 6.0 & 6.0 & 8.0 & 7.24 & 6.13 & 6.08 & 5.25 & 7 \\\\\n",
"\t8 & 4.0 & 4.0 & 4.0 & 19.0 & 4.26 & 3.1 & 5.39 & 12.5 & 8 \\\\\n",
"\t9 & 12.0 & 12.0 & 12.0 & 8.0 & 10.84 & 9.13 & 8.15 & 5.56 & 9 \\\\\n",
"\t10 & 7.0 & 7.0 & 7.0 & 8.0 & 4.82 & 7.26 & 6.42 & 7.91 & 10 \\\\\n",
"\t11 & 5.0 & 5.0 & 5.0 & 8.0 & 5.68 & 4.74 & 5.73 & 6.89 & 11 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"11×9 DataFrame. Omitted printing of 2 columns\n",
"│ Row │ x1 │ x2 │ x3 │ x4 │ y1 │ y2 │ y3 │\n",
"│ │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤\n",
"│ 1 │ 10.0 │ 10.0 │ 10.0 │ 8.0 │ 8.04 │ 9.14 │ 7.46 │\n",
"│ 2 │ 8.0 │ 8.0 │ 8.0 │ 8.0 │ 6.95 │ 8.14 │ 6.77 │\n",
"│ 3 │ 13.0 │ 13.0 │ 13.0 │ 8.0 │ 7.58 │ 8.74 │ 12.74 │\n",
"│ 4 │ 9.0 │ 9.0 │ 9.0 │ 8.0 │ 8.81 │ 8.77 │ 7.11 │\n",
"│ 5 │ 11.0 │ 11.0 │ 11.0 │ 8.0 │ 8.33 │ 9.26 │ 7.81 │\n",
"│ 6 │ 14.0 │ 14.0 │ 14.0 │ 8.0 │ 9.96 │ 8.1 │ 8.84 │\n",
"│ 7 │ 6.0 │ 6.0 │ 6.0 │ 8.0 │ 7.24 │ 6.13 │ 6.08 │\n",
"│ 8 │ 4.0 │ 4.0 │ 4.0 │ 19.0 │ 4.26 │ 3.1 │ 5.39 │\n",
"│ 9 │ 12.0 │ 12.0 │ 12.0 │ 8.0 │ 10.84 │ 9.13 │ 8.15 │\n",
"│ 10 │ 7.0 │ 7.0 │ 7.0 │ 8.0 │ 4.82 │ 7.26 │ 6.42 │\n",
"│ 11 │ 5.0 │ 5.0 │ 5.0 │ 8.0 │ 5.68 │ 4.74 │ 5.73 │"
]
},
"execution_count": 17,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"df.id = 1:nrow(df) # also writing axes(df, 1) on the right hand side would work\n",
"df"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Similarly to `nrow` which gives us a number of rows in a data frame, one can use `ncol` function to get its number of columns."
]
},
{
"cell_type": "code",
"execution_count": 18,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"9"
]
},
"execution_count": 18,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"ncol(df)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"In order to practice what we have already learnt let us create a new data frame which will have `:id` coumn in front of the remaining columns."
]
},
{
"cell_type": "code",
"execution_count": 19,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"id x1 x2 x3 x4 y1 y2 y3 y4 Int64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 11 rows × 9 columns
1 1 10.0 10.0 10.0 8.0 8.04 9.14 7.46 6.58 2 2 8.0 8.0 8.0 8.0 6.95 8.14 6.77 5.76 3 3 13.0 13.0 13.0 8.0 7.58 8.74 12.74 7.71 4 4 9.0 9.0 9.0 8.0 8.81 8.77 7.11 8.84 5 5 11.0 11.0 11.0 8.0 8.33 9.26 7.81 8.47 6 6 14.0 14.0 14.0 8.0 9.96 8.1 8.84 7.04 7 7 6.0 6.0 6.0 8.0 7.24 6.13 6.08 5.25 8 8 4.0 4.0 4.0 19.0 4.26 3.1 5.39 12.5 9 9 12.0 12.0 12.0 8.0 10.84 9.13 8.15 5.56 10 10 7.0 7.0 7.0 8.0 4.82 7.26 6.42 7.91 11 11 5.0 5.0 5.0 8.0 5.68 4.74 5.73 6.89
"
],
"text/latex": [
"\\begin{tabular}{r|ccccccccc}\n",
"\t& id & x1 & x2 & x3 & x4 & y1 & y2 & y3 & y4\\\\\n",
"\t\\hline\n",
"\t& Int64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64\\\\\n",
"\t\\hline\n",
"\t1 & 1 & 10.0 & 10.0 & 10.0 & 8.0 & 8.04 & 9.14 & 7.46 & 6.58 \\\\\n",
"\t2 & 2 & 8.0 & 8.0 & 8.0 & 8.0 & 6.95 & 8.14 & 6.77 & 5.76 \\\\\n",
"\t3 & 3 & 13.0 & 13.0 & 13.0 & 8.0 & 7.58 & 8.74 & 12.74 & 7.71 \\\\\n",
"\t4 & 4 & 9.0 & 9.0 & 9.0 & 8.0 & 8.81 & 8.77 & 7.11 & 8.84 \\\\\n",
"\t5 & 5 & 11.0 & 11.0 & 11.0 & 8.0 & 8.33 & 9.26 & 7.81 & 8.47 \\\\\n",
"\t6 & 6 & 14.0 & 14.0 & 14.0 & 8.0 & 9.96 & 8.1 & 8.84 & 7.04 \\\\\n",
"\t7 & 7 & 6.0 & 6.0 & 6.0 & 8.0 & 7.24 & 6.13 & 6.08 & 5.25 \\\\\n",
"\t8 & 8 & 4.0 & 4.0 & 4.0 & 19.0 & 4.26 & 3.1 & 5.39 & 12.5 \\\\\n",
"\t9 & 9 & 12.0 & 12.0 & 12.0 & 8.0 & 10.84 & 9.13 & 8.15 & 5.56 \\\\\n",
"\t10 & 10 & 7.0 & 7.0 & 7.0 & 8.0 & 4.82 & 7.26 & 6.42 & 7.91 \\\\\n",
"\t11 & 11 & 5.0 & 5.0 & 5.0 & 8.0 & 5.68 & 4.74 & 5.73 & 6.89 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"11×9 DataFrame. Omitted printing of 2 columns\n",
"│ Row │ id │ x1 │ x2 │ x3 │ x4 │ y1 │ y2 │\n",
"│ │ \u001b[90mInt64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼───────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤\n",
"│ 1 │ 1 │ 10.0 │ 10.0 │ 10.0 │ 8.0 │ 8.04 │ 9.14 │\n",
"│ 2 │ 2 │ 8.0 │ 8.0 │ 8.0 │ 8.0 │ 6.95 │ 8.14 │\n",
"│ 3 │ 3 │ 13.0 │ 13.0 │ 13.0 │ 8.0 │ 7.58 │ 8.74 │\n",
"│ 4 │ 4 │ 9.0 │ 9.0 │ 9.0 │ 8.0 │ 8.81 │ 8.77 │\n",
"│ 5 │ 5 │ 11.0 │ 11.0 │ 11.0 │ 8.0 │ 8.33 │ 9.26 │\n",
"│ 6 │ 6 │ 14.0 │ 14.0 │ 14.0 │ 8.0 │ 9.96 │ 8.1 │\n",
"│ 7 │ 7 │ 6.0 │ 6.0 │ 6.0 │ 8.0 │ 7.24 │ 6.13 │\n",
"│ 8 │ 8 │ 4.0 │ 4.0 │ 4.0 │ 19.0 │ 4.26 │ 3.1 │\n",
"│ 9 │ 9 │ 12.0 │ 12.0 │ 12.0 │ 8.0 │ 10.84 │ 9.13 │\n",
"│ 10 │ 10 │ 7.0 │ 7.0 │ 7.0 │ 8.0 │ 4.82 │ 7.26 │\n",
"│ 11 │ 11 │ 5.0 │ 5.0 │ 5.0 │ 8.0 │ 5.68 │ 4.74 │"
]
},
"execution_count": 19,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"select(df, \"id\", :)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Note that this time `df` data frame was not changed, as `select` makes a copy."
]
},
{
"cell_type": "code",
"execution_count": 20,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"x1 x2 x3 x4 y1 y2 y3 y4 id Float64 Float64 Float64 Float64 Float64 Float64 Float64 Float64 Int64 11 rows × 9 columns
1 10.0 10.0 10.0 8.0 8.04 9.14 7.46 6.58 1 2 8.0 8.0 8.0 8.0 6.95 8.14 6.77 5.76 2 3 13.0 13.0 13.0 8.0 7.58 8.74 12.74 7.71 3 4 9.0 9.0 9.0 8.0 8.81 8.77 7.11 8.84 4 5 11.0 11.0 11.0 8.0 8.33 9.26 7.81 8.47 5 6 14.0 14.0 14.0 8.0 9.96 8.1 8.84 7.04 6 7 6.0 6.0 6.0 8.0 7.24 6.13 6.08 5.25 7 8 4.0 4.0 4.0 19.0 4.26 3.1 5.39 12.5 8 9 12.0 12.0 12.0 8.0 10.84 9.13 8.15 5.56 9 10 7.0 7.0 7.0 8.0 4.82 7.26 6.42 7.91 10 11 5.0 5.0 5.0 8.0 5.68 4.74 5.73 6.89 11
"
],
"text/latex": [
"\\begin{tabular}{r|ccccccccc}\n",
"\t& x1 & x2 & x3 & x4 & y1 & y2 & y3 & y4 & id\\\\\n",
"\t\\hline\n",
"\t& Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Float64 & Int64\\\\\n",
"\t\\hline\n",
"\t1 & 10.0 & 10.0 & 10.0 & 8.0 & 8.04 & 9.14 & 7.46 & 6.58 & 1 \\\\\n",
"\t2 & 8.0 & 8.0 & 8.0 & 8.0 & 6.95 & 8.14 & 6.77 & 5.76 & 2 \\\\\n",
"\t3 & 13.0 & 13.0 & 13.0 & 8.0 & 7.58 & 8.74 & 12.74 & 7.71 & 3 \\\\\n",
"\t4 & 9.0 & 9.0 & 9.0 & 8.0 & 8.81 & 8.77 & 7.11 & 8.84 & 4 \\\\\n",
"\t5 & 11.0 & 11.0 & 11.0 & 8.0 & 8.33 & 9.26 & 7.81 & 8.47 & 5 \\\\\n",
"\t6 & 14.0 & 14.0 & 14.0 & 8.0 & 9.96 & 8.1 & 8.84 & 7.04 & 6 \\\\\n",
"\t7 & 6.0 & 6.0 & 6.0 & 8.0 & 7.24 & 6.13 & 6.08 & 5.25 & 7 \\\\\n",
"\t8 & 4.0 & 4.0 & 4.0 & 19.0 & 4.26 & 3.1 & 5.39 & 12.5 & 8 \\\\\n",
"\t9 & 12.0 & 12.0 & 12.0 & 8.0 & 10.84 & 9.13 & 8.15 & 5.56 & 9 \\\\\n",
"\t10 & 7.0 & 7.0 & 7.0 & 8.0 & 4.82 & 7.26 & 6.42 & 7.91 & 10 \\\\\n",
"\t11 & 5.0 & 5.0 & 5.0 & 8.0 & 5.68 & 4.74 & 5.73 & 6.89 & 11 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"11×9 DataFrame. Omitted printing of 2 columns\n",
"│ Row │ x1 │ x2 │ x3 │ x4 │ y1 │ y2 │ y3 │\n",
"│ │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │ \u001b[90mFloat64\u001b[39m │\n",
"├─────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┼─────────┤\n",
"│ 1 │ 10.0 │ 10.0 │ 10.0 │ 8.0 │ 8.04 │ 9.14 │ 7.46 │\n",
"│ 2 │ 8.0 │ 8.0 │ 8.0 │ 8.0 │ 6.95 │ 8.14 │ 6.77 │\n",
"│ 3 │ 13.0 │ 13.0 │ 13.0 │ 8.0 │ 7.58 │ 8.74 │ 12.74 │\n",
"│ 4 │ 9.0 │ 9.0 │ 9.0 │ 8.0 │ 8.81 │ 8.77 │ 7.11 │\n",
"│ 5 │ 11.0 │ 11.0 │ 11.0 │ 8.0 │ 8.33 │ 9.26 │ 7.81 │\n",
"│ 6 │ 14.0 │ 14.0 │ 14.0 │ 8.0 │ 9.96 │ 8.1 │ 8.84 │\n",
"│ 7 │ 6.0 │ 6.0 │ 6.0 │ 8.0 │ 7.24 │ 6.13 │ 6.08 │\n",
"│ 8 │ 4.0 │ 4.0 │ 4.0 │ 19.0 │ 4.26 │ 3.1 │ 5.39 │\n",
"│ 9 │ 12.0 │ 12.0 │ 12.0 │ 8.0 │ 10.84 │ 9.13 │ 8.15 │\n",
"│ 10 │ 7.0 │ 7.0 │ 7.0 │ 8.0 │ 4.82 │ 7.26 │ 6.42 │\n",
"│ 11 │ 5.0 │ 5.0 │ 5.0 │ 8.0 │ 5.68 │ 4.74 │ 5.73 │"
]
},
"execution_count": 20,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"df"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"It is also easy to transform a data frame back to a matrix using the `Matrix` function."
]
},
{
"cell_type": "code",
"execution_count": 21,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11×9 Array{Float64,2}:\n",
" 10.0 10.0 10.0 8.0 8.04 9.14 7.46 6.58 1.0\n",
" 8.0 8.0 8.0 8.0 6.95 8.14 6.77 5.76 2.0\n",
" 13.0 13.0 13.0 8.0 7.58 8.74 12.74 7.71 3.0\n",
" 9.0 9.0 9.0 8.0 8.81 8.77 7.11 8.84 4.0\n",
" 11.0 11.0 11.0 8.0 8.33 9.26 7.81 8.47 5.0\n",
" 14.0 14.0 14.0 8.0 9.96 8.1 8.84 7.04 6.0\n",
" 6.0 6.0 6.0 8.0 7.24 6.13 6.08 5.25 7.0\n",
" 4.0 4.0 4.0 19.0 4.26 3.1 5.39 12.5 8.0\n",
" 12.0 12.0 12.0 8.0 10.84 9.13 8.15 5.56 9.0\n",
" 7.0 7.0 7.0 8.0 4.82 7.26 6.42 7.91 10.0\n",
" 5.0 5.0 5.0 8.0 5.68 4.74 5.73 6.89 11.0"
]
},
"execution_count": 21,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"Matrix(df)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We will use this feature to determine a plotting range for our data."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
" We take the extrema respectively of the \"x\" and \"y\" variables, add padding equal to 1, and finally collect them to vectors (without calling the `collect` our result would be a `Tuple`)"
]
},
{
"cell_type": "code",
"execution_count": 22,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"2-element Array{Float64,1}:\n",
" 3.0\n",
" 20.0"
]
},
"execution_count": 22,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"xlim = collect(extrema(Matrix(select(df, r\"x\"))) .+ (-1, 1))"
]
},
{
"cell_type": "code",
"execution_count": 23,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"2-element Array{Float64,1}:\n",
" 2.1\n",
" 13.74"
]
},
"execution_count": 23,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"ylim = collect(extrema(Matrix(select(df, r\"y\"))) .+ (-1, 1))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Now we are ready to produce the final plots.\n",
"\n",
"Note that the GLM.jl package is integrated with DataFrames.jl and in `lm` and `predict` functions we can use data frame objects to pass data.\n",
"\n",
"Note though that as GLM.jl in general supports other tabular types than just DataFrames.jl it is more strict and accepts only `Symbol`s as column names (this is required when we use the `term` function)."
]
},
{
"cell_type": "code",
"execution_count": 24,
"metadata": {},
"outputs": [
{
"data": {
"image/png": "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",
"text/plain": [
"Figure(PyObject )"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"fig, axs = plt.subplots(2, 2)\n",
"fig.tight_layout(pad=4.0)\n",
"for i in 1:4\n",
" x = Symbol(\"x\", i)\n",
" y = Symbol(\"y\", i)\n",
" model = lm(term(y)~term(x), df)\n",
" axs[i].plot(xlim, predict(model, DataFrame(x => xlim)), color=\"orange\")\n",
" axs[i].scatter(df[:, x], df[:, y])\n",
" axs[i].set_xlim(xlim)\n",
" axs[i].set_ylim(ylim)\n",
" axs[i].set_xlabel(\"x$i\")\n",
" axs[i].set_ylabel(\"y$i\")\n",
" a, b = round.(coef(model), digits=2)\n",
" c = round(100 * r2(model), digits=2)\n",
" axs[i].set_title(string(\"R²=$c%, $y=$a+$b$x\"))\n",
"end"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"We note that in all cases the estimated models have exactly the same R² and estimated coefficients."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"It is worth to highlight several important features of DataFrames.jl package functionality that we used in the above example."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"First, it is easy to create a data frame from variables holding column names and values using `=>`. Here is one more example how this functionality can be used:"
]
},
{
"cell_type": "code",
"execution_count": 25,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"var1 var2 Int64 Int64 3 rows × 2 columns
1 1 4 2 2 5 3 3 6
"
],
"text/latex": [
"\\begin{tabular}{r|cc}\n",
"\t& var1 & var2\\\\\n",
"\t\\hline\n",
"\t& Int64 & Int64\\\\\n",
"\t\\hline\n",
"\t1 & 1 & 4 \\\\\n",
"\t2 & 2 & 5 \\\\\n",
"\t3 & 3 & 6 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"3×2 DataFrame\n",
"│ Row │ var1 │ var2 │\n",
"│ │ \u001b[90mInt64\u001b[39m │ \u001b[90mInt64\u001b[39m │\n",
"├─────┼───────┼───────┤\n",
"│ 1 │ 1 │ 4 │\n",
"│ 2 │ 2 │ 5 │\n",
"│ 3 │ 3 │ 6 │"
]
},
"execution_count": 25,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"x = :var1\n",
"y = :var2\n",
"xc = 1:3\n",
"yc = 4:6\n",
"DataFrame(x => xc, y => yc)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Note that the same effect can be achieved with passing keyword arguments directly to `DataFrame` constructor:"
]
},
{
"cell_type": "code",
"execution_count": 26,
"metadata": {},
"outputs": [
{
"data": {
"text/html": [
"var1 var2 Int64 Int64 3 rows × 2 columns
1 1 4 2 2 5 3 3 6
"
],
"text/latex": [
"\\begin{tabular}{r|cc}\n",
"\t& var1 & var2\\\\\n",
"\t\\hline\n",
"\t& Int64 & Int64\\\\\n",
"\t\\hline\n",
"\t1 & 1 & 4 \\\\\n",
"\t2 & 2 & 5 \\\\\n",
"\t3 & 3 & 6 \\\\\n",
"\\end{tabular}\n"
],
"text/plain": [
"3×2 DataFrame\n",
"│ Row │ var1 │ var2 │\n",
"│ │ \u001b[90mInt64\u001b[39m │ \u001b[90mInt64\u001b[39m │\n",
"├─────┼───────┼───────┤\n",
"│ 1 │ 1 │ 4 │\n",
"│ 2 │ 2 │ 5 │\n",
"│ 3 │ 3 │ 6 │"
]
},
"execution_count": 26,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"DataFrame(var1=xc, var2=yc)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Another thing you might have noticed is the use of `df[:, x]` and `df[:, y]` indexing expressions to get columns from a data frame. Let us comment on the differences between `df.col` and `df[:, col]` syntaxes that we discussed above:"
]
},
{
"cell_type": "code",
"execution_count": 27,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11-element Array{Float64,1}:\n",
" 10.0\n",
" 8.0\n",
" 13.0\n",
" 9.0\n",
" 11.0\n",
" 14.0\n",
" 6.0\n",
" 4.0\n",
" 12.0\n",
" 7.0\n",
" 5.0"
]
},
"execution_count": 27,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"# gives you a direct access to the column stored in `df` but x1 is a literal\n",
"df.x1"
]
},
{
"cell_type": "code",
"execution_count": 28,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11-element Array{Float64,1}:\n",
" 10.0\n",
" 8.0\n",
" 13.0\n",
" 9.0\n",
" 11.0\n",
" 14.0\n",
" 6.0\n",
" 4.0\n",
" 12.0\n",
" 7.0\n",
" 5.0"
]
},
"execution_count": 28,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"# now the column is copied, so this is the same as copy(df.x1)\n",
"# in this case we could have used a variable instead of a literal for indexing\n",
"df[:, :x1]"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"So what if you want to select a column without copying it but want to use a variable holding its name. There is a special `!` row selector for this:"
]
},
{
"cell_type": "code",
"execution_count": 29,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
":x1"
]
},
"execution_count": 29,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"n = :x1"
]
},
{
"cell_type": "code",
"execution_count": 30,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"11-element Array{Float64,1}:\n",
" 10.0\n",
" 8.0\n",
" 13.0\n",
" 9.0\n",
" 11.0\n",
" 14.0\n",
" 6.0\n",
" 4.0\n",
" 12.0\n",
" 7.0\n",
" 5.0"
]
},
"execution_count": 30,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"v = df[!, n]"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Let us check that `!` does not copy:"
]
},
{
"cell_type": "code",
"execution_count": 31,
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"true"
]
},
"execution_count": 31,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"v === df.x1"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Indexing of a data frame is very flexible. All rules governing this functionality can be found at https://juliadata.github.io/DataFrames.jl/stable/lib/indexing/."
]
}
],
"metadata": {
"@webio": {
"lastCommId": null,
"lastKernelId": null
},
"kernelspec": {
"display_name": "Julia 1.4.1",
"language": "julia",
"name": "julia-1.4"
},
"language_info": {
"file_extension": ".jl",
"mimetype": "application/julia",
"name": "julia",
"version": "1.4.1"
}
},
"nbformat": 4,
"nbformat_minor": 4
}