Octave:用向量替换matix / vector的元素

时间:2016-07-07 16:41:41

标签: octave

我试图将矩阵中的每个元素从1到10的值转换为10x1零点矩阵,其中零元素矩阵的元素对应于原始元素的值等于1.

以下是代码:

function q = convert

% Convert y matrix values to 10x1 vector

load('y.mat');

ZERO = zeros(10,1);

% Set 10x1 Matrix of zeros

for i = 1:length(y)

   ZERO(y(i)) = 1; % Set yth element of ZERO to 1

   y(i) = ZERO;    % Set ith element of y equal to new zero

   ZERO = zeros(10,1); % Re-establish zero

endfor

当我运行它时,我收到错误A(I) = X: X must have the same size as I。我试图输入的矩阵与矩阵y的元素大小不一致。我可以解决这个问题吗?

示例输入:

y = [1; 2; 3; 4; 5] 

示例输出:

y = [[1;0;0;0;0;0;0;0;0;0], 
     [0;1;0;0;0;0;0;0;0;0], 
     [0;0;1;0;0;0;0;0;0;0],
     [0;0;0;0;1;0;0;0;0;0],
     [0;0;0;0;0;1;0;0;0;0]]

1 个答案:

答案 0 :(得分:1)

我将做出几个假设:

  1. 您希望返回值为q,如函数签名和
  2. 您希望样本案例中的输出为10x5矩阵,如下所示:

    1   0   0   0   0
    0   1   0   0   0
    0   0   1   0   0
    0   0   0   1   0
    0   0   0   0   1
    0   0   0   0   0
    0   0   0   0   0
    0   0   0   0   0
    0   0   0   0   0
    0   0   0   0   0
    
  3. 修复循环

    出现错误的问题是,您要将10x1向量ZERO分配给5x1向量y的单个(标量)元素:

    y(i) = ZERO;
    

    矢量不适合标量。但即使您更改此选项以将ZERO分配给y列,它也不合适,因为列的长度不同。这不是你想要做的事情,因为如果它有效,你就会消除y中的值。因此,让我们在输出数组q的列中设置值。 (更改在评论中标有<==。)

    function q = convert
    % Convert y matrix values to 10xn matrix
    
    %load('y.mat');
    y = [1; 2; 3; 4; 5];   % <== replace load temporarily
    
    % Set 10x1 Matrix of zeros
    ZERO = zeros(10,1);
    % Preallocate output array
    q = zeros(10, length(y));   % <== preallocate for speed
    
    for i = 1:length(y)
      ZERO(y(i)) = 1;     % Set yth element of ZERO to 1
      q(:,i) = ZERO;      % <== Set ith *column* of *q* equal to new zero
      ZERO = zeros(10,1); % Re-establish zero
    endfor
    

    改善循环

    这会有效,但是如果您预先分配q,那么您已经获得了正确数量的ZERO向量,那么为什么不直接设置这些值?

    function q = convert
    % Convert y matrix values to 10xn matrix
    
    %load('y.mat');
    y = [1; 2; 3; 4; 5];   % <== replace load temporarily
    
    % Preallocate output array
    q = zeros(10, length(y));   % <== preallocate for speed
    
    for i = 1:length(y)
      q(y(i),i) = 1;      % <== Set element at y(ith) row and ith column of q to 1
    endfor
    

    杀死循环

    这些循环中的任何一个都会为您提供所需的结果,但您可以在没有循环的情况下完成整个操作。 This answer总结了执行此操作的不同方法,但我只会使用sub2ind向您展示第一个方法:

    function q = convert
    % Convert y matrix values to 10xn matrix
    
    %load('y.mat');
    y = [1; 2; 3; 4; 5];   % <== replace load temporarily
    
    % Preallocate output array
    q = zeros(10, length(y));   % <== preallocate for speed
    
    idx = sub2ind(size(q), y, [1:length(y)].');
    q(idx) = 1;
    

    最后的注释

    最好不要在Octave / MATLAB中使用i作为变量名。它在其他语言中很自然,但在MATLAB中i(或j)是imaginary unit。如果使用i作为变量,它会将该阴影视为常量。如果您在分配复杂值时使用1i(或1j),这并没有什么不同,但您必须记住这样做,并且在某些时候您需要#&# 39;重新忘记。