spectralnorm.pp 1.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667
  1. { The Computer Language Shootout
  2. http://shootout.alioth.debian.org
  3. contributed by Ian Osgood
  4. modified by Vincent Snijders
  5. }
  6. program spectralNorm;
  7. {$mode objfpc}{$inline on}
  8. var n,i : integer;
  9. u,v,tmp : array of double;
  10. vBv,vv : double;
  11. function A(i,j : integer): double; inline;
  12. begin
  13. A := 1 / ((i+j)*(i+j+1) div 2 + i+1);
  14. end;
  15. procedure mulAv(var v, Av : array of double);
  16. var i,j : integer;
  17. begin
  18. for i := low(Av) to high(Av) do
  19. begin
  20. Av[i] := 0.0;
  21. for j := low(v) to high(v) do
  22. Av[i] := Av[i] + A(i,j) * v[j];
  23. end;
  24. end;
  25. procedure mulAtv(var v, Atv : array of double);
  26. var i,j : integer;
  27. begin
  28. for i := low(Atv) to high(Atv) do
  29. begin
  30. Atv[i] := 0.0;
  31. for j := low(v) to high(v) do
  32. Atv[i] := Atv[i] + A(j,i) * v[j];
  33. end;
  34. end;
  35. procedure mulAtAv(var v, AtAv : array of double);
  36. begin
  37. mulAv(v, tmp);
  38. mulAtv(tmp, AtAv);
  39. end;
  40. begin
  41. Val(paramstr(1), n, i);
  42. SetLength(u, n);
  43. SetLength(v, n);
  44. SetLength(tmp, n);
  45. for i := low(u) to high(u) do u[i] := 1.0;
  46. for i := 1 to 10 do begin mulAtAv(u,v); mulAtAv(v,u) end;
  47. for i := low(u) to high(u) do
  48. begin
  49. vBv := vBv + u[i]*v[i];
  50. vv := vv + v[i]*v[i];
  51. end;
  52. writeln(sqrt(vBv/vv):0:9);
  53. end.