fozziethebeat / S-Space

The S-Space repsitory, from the AIrhead-Research group
GNU General Public License v2.0
203 stars 106 forks source link

1 test fails - SingularValueDecompositionOctaveTest #37

Closed tuxdna closed 6 years ago

tuxdna commented 11 years ago

Originally reported here: https://groups.google.com/forum/?fromgroups=#!topic/s-space-research-dev/Ycy0tWlOnLs

Failed tests: testMatrixReduction(edu.ucla.sspace.matrix.factorization.SingularValueDecompositionOctaveTest): expected:<0.8945379188> but was:<-0.8945360178645925>

tuxdna commented 11 years ago

On further investigation, I found that Octave is actually giving a -ve value i.e. -0.89454. However as per the test-case a +ve value is expected i.e. 0.89454.

$ cat /tmp/svd-octave.dat 1 1 1.0 1 2 1.0 1 7 1.0 2 2 1.0 2 3 1.0 3 1 1.0 4 4 1.0 4 5 1.0 4 6 1.0 5 4 1.0 5 6 1.0 5 7 1.0 $ octave GNU Octave, version 3.2.4 octave:1> Z = load('/tmp/svd-octave.dat','-ascii') warning: load: loaded ASCII file `/tmp/svd-octave.dat' -- ignoring extra args Z =

1 1 1 1 2 1 1 7 1 2 2 1 2 3 1 3 1 1 4 4 1 4 5 1 4 6 1 5 4 1 5 6 1 5 7 1

octave:2> A = spconvert(Z) A =

Compressed Column Sparse (rows = 5, cols = 7, nnz = 12 [34%])

(1, 1) -> 1 (3, 1) -> 1 (1, 2) -> 1 (2, 2) -> 1 (2, 3) -> 1 (4, 4) -> 1 (5, 4) -> 1 (4, 5) -> 1 (4, 6) -> 1 (5, 6) -> 1 (1, 7) -> 1 (5, 7) -> 1

octave:3> clear Z octave:4> [U, S, V] = svds(A, 2) U =

-0.388460 -0.736150 -0.117616 -0.425017 -0.090281 -0.269450 -0.596357 0.425017 -0.686639 0.155567

S =

Diagonal Matrix

2.3028 0 0 1.9319

V =

-0.207897 -0.520537 -0.219768 -0.601064 -0.051076 -0.220005 -0.557152 0.300532 -0.258973 0.220005 -0.557152 0.300532 -0.466871 -0.300532

octave:5> U(1)(1) * S(1) ans = -0.89454

davidjurgens commented 11 years ago

Hi Saleem,

This is interesting! The SVD does not have a unique solution, so it looks like Octave is finding a solution than we expect, with a singular value that has the opposite sign of what we expect. (I suspect the other singular values would have opposite signs as well.) We could potentially revise the unit test so that it checks against the absolute value. Octave's value and the expected value are nearly identical when the sign is ignored, so I think this should work.

Thanks, David

On Thu, May 9, 2013 at 11:09 AM, Saleem Ansari notifications@github.comwrote:

On further investigation, I found that Octave is actually giving a -ve value i.e. -0.89454. However as per the test-case a +ve value is expected i.e. 0.89454.

$ cat /tmp/svd-octave.dat 1 1 1.0 1 2 1.0 1 7 1.0 2 2 1.0 2 3 1.0 3 1 1.0 4 4 1.0 4 5 1.0 4 6 1.0 5 4 1.0 5 6 1.0 5 7 1.0 $ octave GNU Octave, version 3.2.4 octave:1> Z = load('/tmp/svd-octave.dat','-ascii') warning: load: loaded ASCII file `/tmp/svd-octave.dat' -- ignoring extra args Z =

1 1 1 1 2 1 1 7 1 2 2 1 2 3 1 3 1 1 4 4 1 4 5 1 4 6 1 5 4 1 5 6 1 5 7 1

octave:2> A = spconvert(Z) A =

Compressed Column Sparse (rows = 5, cols = 7, nnz = 12 [34%])

(1, 1) -> 1 (3, 1) -> 1 (1, 2) -> 1 (2, 2) -> 1 (2, 3) -> 1 (4, 4) -> 1 (5, 4) -> 1 (4, 5) -> 1 (4, 6) -> 1 (5, 6) -> 1 (1, 7) -> 1 (5, 7) -> 1

octave:3> clear Z octave:4> [U, S, V] = svds(A, 2) U =

-0.388460 -0.736150 -0.117616 -0.425017 -0.090281 -0.269450 -0.596357 0.425017 -0.686639 0.155567

S =

Diagonal Matrix

2.3028 0 0 1.9319

V =

-0.207897 -0.520537 -0.219768 -0.601064 -0.051076 -0.220005 -0.557152 0.300532 -0.258973 0.220005 -0.557152 0.300532 -0.466871 -0.300532

octave:5> U(1)(1) * S(1) ans = -0.89454

— Reply to this email directly or view it on GitHubhttps://github.com/fozziethebeat/S-Space/issues/37#issuecomment-17655750 .

tuxdna commented 11 years ago

Well, in-fact, the signs of expected and actual values sometimes match:

Check U now... r:0, c:0, expected: 0.894538, actual: -0.894536 r:0, c:1, expected: -1.422131, actual: -1.422133 r:1, c:0, expected: 0.270844, actual: -0.270844 r:1, c:1, expected: -0.821069, actual: -0.821069 r:2, c:0, expected: 0.207898, actual: -0.207897 r:2, c:1, expected: -0.520537, actual: -0.520537 r:3, c:0, expected: 1.373279, actual: -1.373277 r:3, c:1, expected: 0.821069, actual: 0.821069 r:4, c:0, expected: 1.581179, actual: -1.581175 r:4, c:1, expected: 0.300532, actual: 0.300532 Check V now... r:0, c:0, expected: 0.478741, actual: -0.478741 r:0, c:1, expected: 0.506077, actual: -0.506076 r:0, c:2, expected: 0.117616, actual: -0.117616 r:0, c:3, expected: 1.282998, actual: -1.282996 r:0, c:4, expected: 0.596358, actual: -0.596357 r:0, c:5, expected: 1.282998, actual: -1.282996 r:0, c:6, expected: 1.075101, actual: -1.075098 r:1, c:0, expected: -1.005599, actual: -1.005600 r:1, c:1, expected: -1.161165, actual: -1.161167 r:1, c:2, expected: -0.425017, actual: -0.425017 r:1, c:3, expected: 0.580583, actual: 0.580584 r:1, c:4, expected: 0.425017, actual: 0.425017 r:1, c:5, expected: 0.580583, actual: 0.580584 r:1, c:6, expected: -0.580583, actual: -0.580584

I don't have an in-depth knowledge of how SVD works. However, if it is safe to ignore the signs of two values, then the test does pass.

tuxdna commented 6 years ago

Closed via https://github.com/fozziethebeat/S-Space/pull/39