2014-02-19 5 views
0

У меня есть массив из 288 значений. он содержит единицы и нули в группе в любой комбинации.Найти начальную и конечную точки группы чисел в массиве

например

[0,0,0,0,0,1,1,1,1,1,1,0,0,0,0,1,1,1,1,0,0,0.1] 
[1,1,1,1,1,1,1,1,1,1,1,1,1,0,0,0,1,1,1,1,1,1,1,1,1,1,0,0,0,0...] 
[1,1,1,1,1,1,1,1,0,0,0,0,0,1,1,1,1,1....] 

он может начинаться и заканчиваться либо группой нуля или группы одного. но гарантируется, что в массиве будет по крайней мере одна группа нулей или единиц. Я заинтересован в сохранении индексов начала и конца группы единиц в массиве. например, 6,16,23 в первом примере в start_index (скажем, это вектор для хранения) и 11,19 в end_index.

Я хочу, чтобы это было общим. так как мой массив может начинаться с любой группы.

Я использую следующий код для реализации этого, но я не увенчался успехом в реализации полной логики. В любом случае, я думаю, что я застрял, как сделать algo. Код ниже - небольшая часть, которую я написал, которая касается только одной возможности.

std::vector<float>start_index 
std::vector<float>end_index 

float alter_value = array[0]; 
for (int i = 0; i < array.size(); i++) 
{ 
    if (alter_value == 0) 
    { 
     if(array[i+1] != alter_value) 
     { 
       start_index.push_back(array[i+1]); 
       alter_value = array[i+1]; // this makes my alter_value = 1 
     } 
    } 
} 

Может быть, я не могу лучше передать то, что хочу. Но, надеюсь, вы понимаете.

ответ

1

Вы можете посмотреть на 1 в массиве, как только он будет найден, запись его местоположение и пропустить все соседние 1s. Как только вы нажмете ноль, вы можете продолжить делать то же самое снова (найдите следующий 1).

Редактированный код выглядит следующим образом. Также обратите внимание на некоторые изменения в декларации.

std::vector<int> start_index 
std::vector<end> end_index 
    for (int i = 0; i < array.size(); i++) 
    { 
     if (array[i] == 1) 
     { 
        start_index.push_back(i); 
        while(array[i] == 1 && i < array.size()) { 
         i++; 
        } 
        //will reach here if array[i] == 0 or array is exhausted 
        end_index.push_back(i - 1); 
     } 
    } 
+0

Вы упомянули end_index.push_back (i - 1) ;. если это не будет end_index.push_back (i) ;? –

+1

@MT Когда вы выходите из цикла, 'array [i] равен 0', вам нужно записать местоположение последнего' 1', которое является 'i - 1'. – axiom

1

Вы хотите хранить индексы, но вместо этого вы храните значения массива. Индексы представляют собой целые числа, так что ваши индексные векторы должны быть vector<int>, а вместо

start_index.push_back(array[i+1]) 

вы должны сделать

start_index.push_back(i+1) 
0

Самый простой способ :)

int last = array[0]; 
    start_index.push_back(0); 
    for (int i = 1; i < array.size(); i++) { 
     if (array[i] != last) { 
      start_index.push_back(i); 
      last = array[i]; 
     } 
    } 
0

Вы можете рассмотреть следующий алгоритм. Это в псевдокоде - я не фанат C++, но переписывать его на любой язык должен быть тривиальным:

Он проходит через весь вход и обнаруживает края групп, сохраняя их в массивах результатов *.

array; // input array 
resultStarts; // array of indexes of starts of groups 
resultEnds; // array of indexes of ends of groups 
searchFor = 1; // element of groups 

inGroup = false; 

for(i=0;i<length(array);i++) { 
if((array[i] == searchFor) && ! inGroup) { 
    // it's start of group 
    inGroup = true; // mark it 
    push(resultStarts, i); 
} 
if(inGroup && ((array[i] != searchFor) || i == length(array))) { 
    // end of group (of the input) 
    inGroup = false; 
    push(resultEnds, i); 
} 
} 
Смежные вопросы