2011-03-10 66 views

回答

2

你可以做一個陣列相同的形狀,包含X列方向是指:

means = repmat(mean(X), [size(X,1) 1]); 
X(X==0) = means(X==0); 

[編輯追加...]

或者,如果陣列冒犯的明確擴張你,你可以這樣做:

X = bsxfun(@(x,y)(x+(x==0)*y), X, mean(X)); 

這是對我的口味有點太「聰明」,但似乎是約25%的速度在我測試的一個案例(1000×1000陣列,約10%是零)。

+0

我喜歡第二個! – ptikobj 2011-03-10 18:39:14

+0

然而,應用第二個產生:「???下標索引必須是真正的正整數或邏輯。」可能是因爲手段(X)? – ptikobj 2011-03-10 18:45:37

+0

糟糕。我的意思是「mean(X)」,而不是「means(X)」。將編輯,道歉的方式,將廢話你的評論:-)。 – 2011-03-10 19:07:34

3

這是一個矢量化解決方案,它比使用BSXFUN更快,並且不需要複製列方法數組。它只是找到對應的列索引的修改每一個線性指標,然後使用該索引,以獲得正確的列均值:

colMeans = mean(X); %# Get the column means 
index = find(X == 0); %# Get the linear indices of the zero values 
colIndex = ceil(index./size(X,1)); %# Get the column index for each linear index 
X(index) = colMeans(colIndex);  %# Reassign zeroes with the column means 

而這裏的測試用例:

>> X = randi([0 1],5) %# Generate a random matrix of zeroes and ones 

X = 

    0  1  0  1  0 
    1  0  0  1  1 
    0  1  0  1  0 
    1  1  1  0  1 
    0  1  0  0  1 

>> colMeans = mean(X); 
>> index = find(X == 0); 
>> colIndex = ceil(index./size(X,1)); 
>> X(index) = colMeans(colIndex) 

X = 

    0.4000 1.0000 0.2000 1.0000 0.6000 
    1.0000 0.8000 0.2000 1.0000 1.0000 
    0.4000 1.0000 0.2000 1.0000 0.6000 
    1.0000 1.0000 1.0000 0.6000 1.0000 
    0.4000 1.0000 0.2000 0.6000 1.0000 
+0

在技術上是一個很好的解決方案,但在什麼情況下,您的實際平均值計算會保持?謝謝 – eat 2011-03-10 20:43:18

+0

@eat:在問題的背景下。 ;)換句話說,我不知道*爲什麼*或*爲了什麼目的* ptikobj想用列平均值替換零值,我只是簡單地展示了它如何有效地完成。 – gnovice 2011-03-10 20:53:08