using PyPlot
using LinearAlgebra
using Statistics
x = randn(10); y = sqrt(0.95) * x + sqrt(0.05) * randn(10);
scatter(x, y);
# fit with linear regression
f = [x ones(10)];
w = y' / f';
xplot = collect(-1.5:0.1:1.5);
fplot = [xplot ones(length(xplot))]
plot(xplot, fplot * w'; color="red");
scatter(x, y);
xlim([-1.5, 1.5]);
ylim([-1.5, 1.5]);
training_error = round(mean((y - f * w').^2); digits=3)
println("training error: $(training_error)")
# fit with degree 10 polynomial
f = hcat([x.^k for k = 0:10]...);
w = y' / f';
xplot = collect(-1.5:0.01:1.5);
fplot = hcat([xplot.^k for k = 0:10]...)
plot(xplot, fplot * w'; color="red");
scatter(x, y);
xlim([-1.5, 1.5]);
ylim([-1.5, 1.5]);
training_error = round(mean((y - f * w').^2); digits=3)
println("training error: $(training_error)")
test_x = randn(20); test_y = sqrt(0.9) * test_x + sqrt(0.1) * randn(20);
# fit with linear regression
f = [x ones(10)];
w = y' / f';
xplot = collect(-1.5:0.1:1.5);
fplot = [xplot ones(length(xplot))]
plot(xplot, fplot * w'; color="red");
scatter(x, y);
scatter(test_x, test_y; color="orange");
xlim([-1.5, 1.5]);
ylim([-1.5, 1.5]);
training_error = round(mean((y - f * w').^2); digits=3)
println("training error: $(training_error)")
test_f = [test_x ones(length(test_x))];
test_error = round(mean((test_y - test_f * w').^2); digits=3)
println("test error: $(test_error)")
# fit with degree 10 polynomial
f = hcat([x.^k / factorial(k) for k = 0:10]...);
w = y' / f';
xplot = collect(-1.5:0.01:1.5);
fplot = hcat([xplot.^k / factorial(k) for k = 0:10]...)
plot(xplot, fplot * w'; color="red");
scatter(x, y);
scatter(test_x, test_y; color="orange");
xlim([-1.5, 1.5]);
ylim([-1.5, 1.5]);
training_error = round(mean((y - f * w').^2); digits=3)
println("training error: $(training_error)")
test_f = hcat([test_x.^k / factorial(k) for k = 0:10]...)
test_error = round(mean((test_y - test_f * w').^2); digits=3)
println("test error: $(test_error)")
Suppose that we use regularization such that for a polynomial of the form $$f_w(x) = \sum_{k = 0}^{10} \frac{w_k x^k}{k!}$$ the loss function is $$h(w) = \sum_{i=1}^N (f_w(x_i) - y_i)^2 + \sigma^2 \| w \|^2.$$ If $A$ is the matrix such that $$ A_{i,j} = \frac{x_i^j}{j!} $$ then equivalently $$h(w) = \left\| \left[\begin{array}{c} A \\ \sigma I \end{array} \right] w - \left[\begin{array}{c} y \\ 0 \end{array} \right] \right\|^2$$ so we can still solve this easily with linear regression.
# fit with regularized degree 10 polynomial
sigma = 0.01
f = hcat([x.^k / factorial(k) for k = 0:10]...);
f_reg = vcat(f, sigma * Matrix{Float64}(I, 11, 11))
y_reg = vcat(y, zeros(11))
w = y_reg' / f_reg';
xplot = collect(-1.5:0.01:1.5);
fplot = hcat([xplot.^k / factorial(k) for k = 0:10]...)
plot(xplot, fplot * w'; color="red");
scatter(x, y);
scatter(test_x, test_y; color="orange");
xlim([-1.5, 1.5]);
ylim([-1.5, 1.5]);
training_error = round(mean((y - f * w').^2); digits=3)
println("training error: $(training_error)")
test_f = hcat([test_x.^k / factorial(k) for k = 0:10]...)
test_error = round(mean((test_y - test_f * w').^2); digits=3)
println("test error: $(test_error)")
function regularized_fit_error(sigma)
test_x = randn(10000); test_y = sqrt(0.9) * test_x + sqrt(0.1) * randn(10000);
f = hcat([x.^k / factorial(k) for k = 0:10]...);
f_reg = vcat(f, sigma * Matrix{Float64}(I, 11, 11))
y_reg = vcat(y, zeros(11))
w = y_reg' / f_reg';
test_f = hcat([test_x.^k / factorial(k) for k = 0:10]...)
training_error = round(mean((y - f * w').^2); digits=3)
test_error = round(mean((test_y - test_f * w').^2); digits=3)
return (training_error, test_error)
end
sigmas = 10 .^ (-3:0.1:2);
training_errors = zeros(length(sigmas));
test_errors = zeros(length(sigmas));
for i = 1:length(sigmas)
(training_errors[i], test_errors[i]) = regularized_fit_error(sigmas[i]);
end
loglog(sigmas, training_errors, label="training error");
loglog(sigmas, test_errors, label="test error");
xlabel("regularization coefficient");
ylabel("error");
legend();