Если вы хотите использовать маскированные массивы, вот упрощенный способ сделать это:
import numpy as np
# create some mock data
R_mat = np.arange(16).reshape(4, 4)
Y_mat = np.random.randint(0, 2, (4, 4))
R_mat
# array([[ 0, 1, 2, 3],
# [ 4, 5, 6, 7],
# [ 8, 9, 10, 11],
# [12, 13, 14, 15]])
Y_mat
# array([[0, 1, 0, 1],
# [0, 1, 1, 0],
# [0, 1, 0, 1],
# [0, 0, 1, 0]])
# compute all row means or all column means at once
# use Y_mat==0 to invert and convert to bool in one go
row_means = np.ma.MaskedArray(R_mat, Y_mat==0).mean(axis=1)
col_means = np.ma.MaskedArray(R_mat, Y_mat==0).mean(axis=0)
row_means
# masked_array(data=[2.0, 5.5, 10.0, 14.0],
# mask=[False, False, False, False],
# fill_value=1e+20)
col_means
# masked_array(data=[--, 5.0, 10.0, 7.0],
# mask=[ True, False, False, False],
# fill_value=1e+20)
# or take just one row or column and get the mean
np.ma.MaskedArray(R_mat, Y_mat==0)[2].mean()
# 10.0
np.ma.MaskedArray(R_mat, Y_mat==0)[:, 0].mean()
# masked
Если по какой-то причине вы хотите избежать маскированных массивов:
nrow, ncol = R_mat.shape
I, J = np.where(Y_mat)
row_means = np.bincount(I, R_mat[I, J], nrow) / np.bincount(I, None, nrow)
J, I = np.where(Y_mat.T)
col_means = np.bincount(J, R_mat[I, J], ncol) / np.bincount(J, None, ncol)
# __main__:1: RuntimeWarning: invalid value encountered in true_divide
row_means
# array([ 2. , 5.5, 10. , 14. ])
col_means
# array([nan, 5., 10., 7.])