Q:

Steepest descent to find the solution to a linear system with a Hilbert matrix

I am using the method of steepest descent to figure out the solution to a linear system with a 5x5 Hilbert matrix. I believe the code is fine in the regard that it gives me the right answer. 
My problem is that:

I think it is taking too many iterations to get to the right answer. I believe I may have missed something in the algorithm but I'm not sure what at this point. 
I am not sure if this is the most effective way to implement the algorithm and additionally, it is a little confusing on which "tol" to pick.

Any insight on these would be appreciated (especially 1.). Thanks!
% Method of Steepest Descent with tol 10^-6
h = hilb(5);                            %Hilbert 5x5 matrix
b = [1;1;1;1;1];                        %solution matrix
solution = zeros(d,1);                  %Initialization 
residual = h*solution - b;
tol = 10^(-6)
count = 0; 

while residual'*residual > tol;
    roe = (residual'*residual)/(residual'*h*residual);
    solution = solution - roe*residual;
    residual = h*solution - b;
    count = count + 1;
end

count 
solution 

%Method of Steepest Descent with tol 10^-12
solution = zeros(d,1);
residual = h*solution - b;
tol = 10^(-12)
count = 0; 

while residual'*residual > tol;
    roe = (residual'*residual)/(residual'*h*residual);
    solution = solution - roe*residual;
    residual = residual - roe*h*residual;
    count = count + 1;
end

count
solution

%another_solution = invhilb(5)*b           %Check for solution

A:

I do not have the knowledge to deal with your problem from a mathematical aspect, but from a programming point of view there is a point I could note.
Indeed you are right. It is taking too many iterations until it gets to the result:
Elapsed time is 6.487824 seconds.

count =

      292945

When you define a step size to approach a final result, the step length has to be optimized. Otherwise you are either too slow in getting close to the answer or you are passing by the optimal answer several times and making a zigzag around it because your step length is too large.
To optimize the step size, I first form a function according to your script (plus some small modifications):
function [solution, count, T] = SDhilb(d, step)
h = hilb(d);
tic
b = ones(d, 1);
solution = zeros(d, 1);
residual = h * solution - b;
res2 = residual' * residual;
tol = 10^(-6);
count = 0;
while res2 > tol;
    roe = res2/(residual' * h * residual);
    solution = solution - step * roe * residual; % here the step size appears
    residual = h * solution - b;
    count = count + 1;
    res2 = residual' * residual; % let's calculate this once per iteration
end
T = toc;

Now using this function for a range of step sizes (0.1:0.1:1.3) and couple of Hilbert matrices (d = 2, 3, 4, 5) it is obvious that 1 is not an efficient step size:

Instead, step = 0.9 seems to be much more efficient. let's see how efficient it is in case of hilb(5):
[result, count, T] = SDhilb(5, 0.9)

result =

    3.1894
  -85.7689
  481.4906
 -894.8742
  519.5830

count =

        1633

T =

    0.0204

Which is more than two orders of magnitude faster.
In a similar way you can try different values of tol to see how dramatical it can influence the speed. In that case there is no optimal value: The smaller the tolerance, the more time you need to wait.

