def test_predict(): (I, J, K) = (5, 3, 2) R = numpy.array( [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12], [13, 14, 15]], dtype=float) M = numpy.ones((I, J)) K = 3 U = numpy.array([[125., 126.], [126., 126.], [126., 126.], [126., 126.], [126., 126.]]) V = numpy.array([[84., 84.], [84., 84.], [84., 84.]]) M_test = numpy.array([[0, 0, 1], [0, 1, 0], [0, 0, 0], [1, 1, 0], [0, 0, 0]]) #R->3,5,10,11, R_pred->21084,21168,21168,21168 MSE = (444408561. + 447872569. + 447660964. + 447618649) / 4. R2 = 1. - (444408561. + 447872569. + 447660964. + 447618649) / ( 4.25**2 + 2.25**2 + 2.75**2 + 3.75**2) #mean=7.25 Rp = 357. / ( math.sqrt(44.75) * math.sqrt(5292.) ) #mean=7.25,var=44.75, mean_pred=21147,var_pred=5292, corr=(-4.25*-63 + -2.25*21 + 2.75*21 + 3.75*21) nmf = NMF(R, M, K) nmf.U = U nmf.V = V performances = nmf.predict(M_test) assert performances['MSE'] == MSE assert performances['R^2'] == R2 assert performances['Rp'] == Rp
def test_run(): # Data generated from W = [[1,2],[3,4]], H = [[4,3],[2,1]] R = [[8, 5], [20, 13]] M = [[1, 1], [1, 0]] K = 2 U = numpy.array([[10, 9], [8, 7]], dtype='f') #2x2 V = numpy.array([[6, 4], [5, 3]], dtype='f') #2x2 nmf = NMF(R, M, K) # Check we get an Exception if W, H are undefined with pytest.raises(AssertionError) as error: nmf.run(0) assert str( error.value ) == "U and V have not been initialised - please run NMF.initialise() first." # Then check for 1 iteration whether the updates work - heck just the first entry of U nmf.U = U nmf.V = V nmf.run(1) U_00 = 10 * (6 * 8 / 96.0 + 5 * 5 / 77.0) / (5.0 + 6.0) #0.74970484061 assert abs(U_00 - nmf.U[0][0]) < 0.000001
def test_compute_I_div(): R = [[1, 2, 0, 4], [5, 0, 7, 0]] M = [[1, 1, 0, 1], [1, 0, 1, 0]] K = 2 U = numpy.array([[1, 2], [3, 4]], dtype='f') #2x2 V = numpy.array([[5, 7, 9, 11], [6, 8, 10, 12]], dtype='f').T #4x2 #R_pred = [[17,23,29,35],[39,53,67,81]] expected_I_div = sum([ 1.0 * math.log(1.0 / 17.0) - 1.0 + 17.0, 2.0 * math.log(2.0 / 23.0) - 2.0 + 23.0, 4.0 * math.log(4.0 / 35.0) - 4.0 + 35.0, 5.0 * math.log(5.0 / 39.0) - 5.0 + 39.0, 7.0 * math.log(7.0 / 67.0) - 7.0 + 67.0 ]) nmf = NMF(R, M, K) nmf.U = U nmf.V = V I_div = nmf.compute_I_div() assert abs(I_div - expected_I_div) < 0.0000001