2011-07-01 20 views
8

Mam tablicę liczb całkowitych, i chcę podzielić tę tablicę, gdzie 0 przychodzi i funkcja, która daje mi punkty podziału.Podziel tablicę w MATLAB

przykład: tablicy: 0 0 0 1 2 4 5 6 6 0 0 0 0 0 22 4 5 6 6 0 0 0 4 4 0

Funkcja musi odesłać liczby:

[ 3 10 ;14 20 ;22 25 ] 

Te liczby są indeksem początku i końca liczb niezerowych.

+0

@amro - to bardziej przypomina odwrotność tego problemu, w którym OP próbuje znaleźć wyspy o niezerowych wartościach. – Kev

+0

@Kev: konwersja na drugą, to tak proste, jak dodanie 'array = (array == 0);' na początku (lub odwrotnie do 'array ~ = 0', w zależności od tego, w jaki sposób patrzysz it) ... – Amro

+0

@amro - prawda, ale nie jest to "dokładny" duplikat. – Kev

Odpowiedz

5

tu proste rozwiązanie wektorowy przy użyciu funkcji DIFF i FIND:

>> array = [0 0 0 1 2 4 5 6 6 0 0 0 0 0 22 4 5 6 6 0 0 0 4 4 0]; %# Sample array 
>> edgeArray = diff([0; (array(:) ~= 0); 0]); 
>> indices = [find(edgeArray > 0)-1 find(edgeArray < 0)] 

indices = 

    3 10 
    14 20 
    22 25 

Powyższy kod działa się tworząc tablicę kolumnowej z tych wskazujących elementy różne od zera, dopełnianie tej tablicy zerami (w przypadku, gdy dowolne z niezerowych przęseł rozciąga się do krawędzi macierzy) i przyjmowanie różnic między elementami. To daje wektor edgeArray z 1 wskazujący początek niezerowego zakresu i -1 wskazujący koniec niezerowego zakresu. Następnie funkcja FIND jest używana do uzyskania wskaźników początków i końców.

Jedna strona notatki/nitpick: nie są to indeksy początków i końców niezerowych przęseł, jak mówisz. Z technicznego punktu widzenia są to indeksy tuż przed po i tuż po końcach niezerowych rozpiętości. Ci może rzeczywiście chcą następujące zamiast:

>> indices = [find(edgeArray > 0) find(edgeArray < 0)-1] 

indices = 

    4  9 
    15 19 
    23 24 
2

Spróbuj

a = [0 0 0 1 2 4 5 6 6 0 0 0 0 0 22 4 5 6 6 0 0 0 4 4 0]; 

%#Places where value was zero and then became non-zero 
logicalOn = a(1:end-1)==0 & a(2:end)~=0; 

%#Places where value was non-zero and then became zero 
logicalOff = a(1:end-1)~=0 & a(2:end)==0; 

%#Build a matrix to store the results 
M = zeros(sum(logicalOn),2); 

%#Indices where value was zero and then became non-zero 
[~,indOn] = find(logicalOn); 

%#Indices where value was non-zero and then became zero 
[~,indOff] = find(logicalOff); 

%#We're looking for the zero AFTER the transition happened 
indOff = indOff + 1; 

%#Fill the matrix with results 
M(:,1) = indOn(:); 
M(:,2) = indOff(:); 

%#Display result 
disp(M); 
2

Na temat, ale z lekkim zmienności:

>>> a= [0 0 0 1 2 4 5 6 6 0 0 0 0 0 22 4 5 6 6 0 0 0 4 4 0]; 
>>> adjust= [0 1]'; 
>>> tmp= reshape(find([0 diff(a== 0)])', 2, []) 
tmp = 
    4 15 23 
    10 20 25 
>>> indices= (tmp- repmat(adjust, 1, size(tmp, 2)))' 
indices = 
    4 9 
    15 19 
    23 24 

Jak gnovice wskazał już na pozycyjnych semantyki związanych indices, będę po prostu dodaj, że dzięki temu rozwiązaniu różne schematy mogą być obsługiwane w bardzo prosty sposób przy obliczaniu indices. Tak więc, na żądanie:

>>> adjust= [1 0]'; 
>>> tmp= reshape(find([0 diff(a== 0)])', 2, []); 
>>> indices= (tmp- repmat(adjust, 1, size(tmp, 2)))' 
indices = 
    3 10 
    14 20 
    22 25