Как узнать, сколько раз группа с указанным значением c присутствует в массиве? - PullRequest
2 голосов
/ 14 апреля 2020

У меня есть матрица 1 на 1000 (1 строка на 1000 столбцов), которая содержит только 0 и 1 в качестве своих элементов. Как я могу узнать, сколько раз 1 повторяется 3 раза подряд.

Если их более 3, необходимо сбросить счет. Таким образом, 4 будет 3 + 1, и это будет считаться только как один случай 3 последовательных 1, но 6 будет 3 + 3, так что это будет считаться как два случая, когда 3 последовательных 1.

Ответы [ 3 ]

2 голосов
/ 14 апреля 2020

Этот подход находит различия между тем, когда A идет от 0 до 1 (нарастающий фронт) и от 1 до 0 (нарастающий фронт). Это дает длины последовательных 1 в каждом блоке. Затем разделите эти числа на 3 и округлите, чтобы получить количество прогонов 3.

Заполнение A с 0 в начале и в конце просто гарантирует, что у нас будет передний фронт в начале, если A начинается с a 1, и у нас есть падающий фронт в конце, если A заканчивается 1.

A = round(rand(1,1000));

% padding with a 0 at the start and end will make this simpler
B = [0,A,0];
rising_edges = ~B(1:end-1) & B(2:end);
falling_edges = B(1:end-1) & ~B(2:end);
lengths_of_ones = find(falling_edges) - find(rising_edges);

N = sum(floor(lengths_of_ones  / 3));

или в гораздо менее читаемых 2 строках:

A = round(rand(1,1000));

B = [0,A,0];
N = sum(floor((find(B(1:end-1) & ~B(2:end)) - find(~B(1:end-1) & B(2:end)))  / 3));
0 голосов
/ 14 апреля 2020

Вот еще один векторизованный способ:

% input
n = 3;
a = [1 1 1 1 0 0 1 1 1 0 0 0 1 1 1 1 1 0 1 1 1 1 1 1 1]
%        x           x           x           x     x      = 5

% output
a0 = [a 0];
b = cumsum( a0 )                         % cumsum
c = diff( [0 b( ~( diff(a0) + 1 ) ) ] )  % number of ones within group
countsOf3 = sum( floor( c/n ) )          % groups of 3

Вам нравится это грязно? Вот одна строка:

countsOf3 = sum(floor(diff([0 getfield(cumsum([a 0]),{~(diff([a 0])+1)})])/n))  
0 голосов
/ 14 апреля 2020

Вы можете определить свои пользовательские функции, как показано ниже

v = randi([0,1],1,1000);

% get runs in cell array
function C = runs(v)
  C{1} = v(1);
  for k = 2:length(v)
    if v(k) == C{end}(end)
      C{end} = [C{end},v(k)];
    else
      C{end+1} = v(k);
    end
  end
end 

% count times of 3 consecutive 1s 
function y = count(x)
  if all(x)
    y = floor(length(x)/3);
  else
    y = 0;
  end
end

sum(cellfun(@count,runs(v)))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...