2012-05-14 27 views
30

Tôi đã thực sự đấu tranh chống lại điều này trong 2 tháng nay. Điều gì tạo nên sự khác biệt này?Triển khai phần gốc Gradient trong quãng tám

hypotheses= X * theta 
temp=(hypotheses-y)' 
temp=X(:,1) * temp 
temp=temp * (1/m) 
temp=temp * alpha 
theta(1)=theta(1)-temp 

hypotheses= X * theta 
temp=(hypotheses-y)' 
temp=temp * (1/m) 
temp=temp * alpha 
theta(2)=theta(2)-temp 



theta(1) = theta(1) - alpha * (1/m) * ((X * theta) - y)' * X(:, 1); 
theta(2) = theta(2) - alpha * (1/m) * ((X * theta) - y)' * X(:, 2); 

Tác phẩm thứ hai hoạt động. Tôi chỉ không chắc chắn tại sao .. Tôi đấu tranh để hiểu sự cần thiết cho ma trận nghịch đảo.

+2

Tôi không nghĩ rằng đây là một thực hiện đúng gradient descent. Bạn cần phải cập nhật. Cả hai thetas của bạn cùng một lúc là chính xác. 'tmpTheta1 = theta (1) - alpha * (1/m) * ((X * theta) - y) '* X (:, 1); tmpTheta2 = theta (2) - alpha * (1/m) * ((X * theta) - y) '* X (:, 2);' 'theta (1) = tmpTheta1;' 'theta (2) = tmpTheta2; ' –

Trả lời

54

gì bạn đang làm trong ví dụ đầu tiên trong khối thứ hai bạn đã bỏ lỡ một bước không có bạn? Tôi giả sử bạn nối X với một vectơ của những cái.

temp=X(:,2) * temp 

Ví dụ cuối cùng sẽ hoạt động nhưng có thể được vector hóa nhiều hơn để đơn giản và hiệu quả hơn.

Tôi cho rằng bạn chỉ có 1 tính năng. nó sẽ làm việc giống nhau với nhiều tính năng vì tất cả những gì xảy ra là bạn thêm một cột phụ vào ma trận X của bạn cho mỗi đối tượng địa lý. Về cơ bản bạn thêm một véc tơ của những người vào x để vectorize đánh chặn.

Bạn có thể cập nhật ma trận 2x1 của theta trong một dòng mã. Với x nối ​​một vector của những người làm cho nó một ma trận nx2 sau đó bạn có thể tính toán h (x) bằng cách nhân với vector theta (2x1), đây là (X * theta) bit.

Phần thứ hai của véc tơ là chuyển đổi (X * theta) - y) cung cấp cho bạn ma trận 1 * n khi nhân với X (ma trận n * 2) về cơ bản sẽ tổng hợp cả hai (h (x) -y) x0 và (h (x) -y) x1. Theo định nghĩa, cả hai đều được thực hiện cùng một lúc. Điều này dẫn đến một ma trận 1 * 2 của theta mới của tôi mà tôi chỉ chuyển đổi một lần nữa để lật xung quanh vectơ để có cùng kích thước với vectơ theta. Sau đó tôi có thể thực hiện phép nhân vô hướng đơn giản bằng phép trừ alpha và vector với theta.

X = data(:, 1); y = data(:, 2); 
m = length(y); 
X = [ones(m, 1), data(:,1)]; 
theta = zeros(2, 1);   

iterations = 2000; 
alpha = 0.001; 

for iter = 1:iterations 
    theta = theta -((1/m) * ((X * theta) - y)' * X)' * alpha; 
end 
+0

tại sao bạn cần chuyển đổi (1/m) * ((X * theta) - y) '* X trong vòng lặp for của bạn? –

+0

Câu hỏi tương tự như Grahm, tại sao toàn bộ biểu thức con bị tranposed? – qbert65536

+0

Kết quả của '((1/m) * ((X * theta) - y) '* X)' là 1x2. 'theta' là 2x1. Vì vậy, bit giữa các dấu ngoặc cần phải được transposed để có cùng kích thước và trừ nó từ 'theta'. – AronVanAmmers

5

Trong trường hợp đầu tiên, nếu X là ma trận 3x2 và theta là ma trận 2x1, thì "giả thuyết" sẽ là ma trận 3x1.

Giả sử y là ma trận 3x1, sau đó bạn có thể thực hiện (giả thuyết - y) và nhận ma trận 3x1, sau đó chuyển vị của 3x1 đó là ma trận 1x3 được gán cho tạm thời.

Sau đó, ma trận 1x3 được đặt thành theta (2), nhưng đây không phải là ma trận.

Hai dòng cuối cùng của mã của bạn hoạt động bởi vì, sử dụng ví dụ mxn tôi ở trên,

(X * theta) 

sẽ là một ma trận 3x1.

Sau đó ma trận 3x1 bị trừ bởi y (ma trận 3x1) và kết quả là ma trận 3x1.

(X * theta) - y 

Vì vậy, việc chuyển ma trận 3x1 là ma trận 1x3.

((X * theta) - y)' 

Cuối cùng, ma trận 1x3 lần ma trận 3x1 sẽ bằng ma trận vô hướng hoặc 1x1, đó là những gì bạn đang tìm kiếm. Tôi chắc rằng bạn đã biết, nhưng chỉ để được triệt để, X (:, 2) là cột thứ hai của ma trận 3x2, làm cho nó một ma trận 3x1.

2

Khi bạn cập nhật bạn cần làm như

Start Loop { 

temp0 = theta0 - (equation_here); 

temp1 = theta1 - (equation_here); 


theta0 = temp0; 

theta1 = temp1; 

} End loop 
-8
. 
. 
. 
. 
. 
. 
. 
. 
. 
Spoiler alert 












m = length(y); % number of training examples 
J_history = zeros(num_iters, 1); 

for iter = 1:num_iters 

% ====================== YOUR CODE HERE ====================== 
% Instructions: Perform a single gradient step on the parameter vector 
%    theta. 
% 
% Hint: While debugging, it can be useful to print out the values 
%  of the cost function (computeCost) and gradient here. 
% ========================== BEGIN =========================== 


t = zeros(2,1); 
J = computeCost(X, y, theta); 
t = theta - ((alpha*((theta'*X') - y'))*X/m)'; 
theta = t; 
J1 = computeCost(X, y, theta); 

if(J1>J), 
    break,fprintf('Wrong alpha'); 
else if(J1==J) 
    break; 
end; 


% ========================== END ============================== 

% Save the cost J in every iteration  
J_history(iter) = sum(computeCost(X, y, theta)); 
end 
end 
+5

ý tưởng là giúp người dùng tiến lên, không đăng các ví dụ đầy đủ cho các bài tập thực tế tại nhà – EdvardM

0
function [theta, J_history] = gradientDescent(X, y, theta, alpha, num_iters) 
% Performs gradient descent to learn theta. Updates theta by taking num_iters 
% gradient steps with learning rate alpha. 

% Number of training examples 
m = length(y); 
% Save the cost J in every iteration in order to plot J vs. num_iters and check for convergence 
J_history = zeros(num_iters, 1); 

for iter = 1:num_iters 
    h = X * theta; 
    stderr = h - y; 
    theta = theta - (alpha/m) * (stderr' * X)'; 
    J_history(iter) = computeCost(X, y, theta); 
end 

end 
Các vấn đề liên quan