我有一个64 X 64矩阵,我需要找到列的平均值。
然而,我需要除以矩阵中非零的总数,而不是除以每列中的元素总数(即64)。
我设法让它适用于单个列,如下所示。作为参考,生成矩阵的函数标题为var mQuickSidebar = (function(mUtil, mApp, $) {
console.log('Function: ', Date.now());
var topbarAside;
var topbarAsideTabs;
var topbarAsideClose;
var topbarAsideToggle;
var topbarAsideContent;
var initMessages = function() {
var messenger = $('#m_quick_sidebar_tabs_messenger');
if (messenger.length === 0) {
return;
}
var messengerMessages = messenger.find('.m-messenger__messages');
var init = function() {
var height = topbarAside.outerHeight(true) -
topbarAsideTabs.outerHeight(true) -
messenger.find('.m-messenger__form').outerHeight(true) - 120;
// init messages scrollable content
messengerMessages.css('height', height);
mApp.initScroller(messengerMessages, {});
};
init();
// reinit on window resize
mUtil.addResizeHandler(init);
};
var initSettings = function() {
var settings = $('#m_quick_sidebar_tabs_settings');
if (settings.length === 0) {
return;
}
// init dropdown tabbable content
var init = function() {
var height = mUtil.getViewPort().height - topbarAsideTabs.outerHeight(true) - 60;
// init settings scrollable content
settings.css('height', height);
mApp.initScroller(settings, {});
};
init();
// reinit on window resize
mUtil.addResizeHandler(init);
};
var initLogs = function() {
// init dropdown tabbable content
var logs = $('#m_quick_sidebar_tabs_logs');
if (logs.length === 0) {
return;
}
var init = function() {
var height = mUtil.getViewPort().height - topbarAsideTabs.outerHeight(true) - 60;
// init settings scrollable content
logs.css('height', height);
mApp.initScroller(logs, {});
};
init();
// reinit on window resize
mUtil.addResizeHandler(init);
};
var initOffcanvasTabs = function() {
initMessages();
initSettings();
initLogs();
};
var initOffcanvas = function() {
topbarAside.mOffcanvas({
class: 'm-quick-sidebar',
overlay: true,
close: topbarAsideClose,
toggle: topbarAsideToggle
});
// run once on first time dropdown shown
topbarAside.mOffcanvas().one('afterShow', function() {
mApp.block(topbarAside);
setTimeout(function() {
mApp.unblock(topbarAside);
topbarAsideContent.removeClass('m--hide');
initOffcanvasTabs();
}, 1000);
});
};
return {
init: function() {
console.log('Inside Init(): ', Date.now());
console.log($('#m_quick_sidebar')); // topbarAside is undefined here!
topbarAside = $('#m_quick_sidebar');
topbarAsideTabs = $('#m_quick_sidebar_tabs');
topbarAsideClose = $('#m_quick_sidebar_close');
topbarAsideToggle = $('#m_quick_sidebar_toggle');
topbarAsideContent = topbarAside.find('.m-quick-sidebar__content');
if (topbarAside.length === 0) {
return;
}
initOffcanvas();
}
};
})(mUtil, mApp, $);
$(document).ready(function() {
console.log('document.ready: ', Date.now());
mQuickSidebar.init();
});
。
fmu2(i,j)
这适用于生成第一列的“平均值”。但是,我在循环此过程时遇到问题,因此我将获得每列的均值。我尝试做一个嵌套的for循环,但它只计算了整个64 X 64矩阵的平均值,而不是一次计算一列。这是我试过的:
q = 0;
for i = 1:64
if fmu2(i,1) ~= 0;
q = q + 1;
end
end
for i = 1:64
mv = (1/q).*sum(fmu2(i,1));
end
就像我说的那样,这只给了我整个矩阵的一个值,而不是每列的64个单独的“均值”。任何帮助将不胜感激。
答案 0 :(得分:2)
首先,不要在循环的每次迭代中调用生成矩阵的函数。这是非常低效的,并且如果您的功能足够复杂以产生副作用,将导致重大问题。将返回值存储在变量中一次,然后从那时开始引用该变量。
其次,你根本不需要任何循环。非零的总数由nnz
函数给出(非零数的缩写)。 sum
函数接受一个可选的维度参数,因此您可以告诉它沿着列而不是沿着行或整个矩阵求和。
m = fmu2(i,1)
averages = sum(m, 1) / nnz(m)
averages
将是一个64个元素的数组,每列的平均值,因为sum(m, 1)
是每列的64个元素和,nnz(m)
是标量。
MATLAB的一大优点是它提供了几乎所有东西的矢量化实现。如果你做得对,你几乎不需要使用显式循环来完成任何数学运算。
答案 1 :(得分:2)
如果您想要非零元素的逐列均值,您可以执行以下操作
m = randi([0,5], 5, 5); % some data
avg = sum(m,1) ./ sum(m~=0,1);
这是一个逐列的值,除以不等于0的元素的列数。结果是一个行向量,其中每个元素是m
中相应列的平均值。
请注意,这非常灵活,您可以使用任何条件代替~=0
。