Russian Qt Forum
Ноябрь 23, 2024, 00:53 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1]   Вниз
  Печать  
Автор Тема: удаление элементов из вектора  (Прочитано 19334 раз)
foufou
Гость
« : Сентябрь 13, 2010, 09:00 »

Есть у меня вектор vector<double>* dat (именно вектор, а не QVector - таково требование заказчика).

Правильно ли я понимаю, что единственный способ удалять из него элементы - это удалять при помощи метода erase по-одному ? Т.е. нельзя удалить сразу пачкой ?
Кроме того, на удаляемый элемент нужно установить итератор, типа вот так:

vector<double>::iterator it = dat->begin();
for (int i = 0; i < index; i++)
{
      it++;
}

А потом могу удалять выбранный элемент из вектора:

dat->erase(it);

Чтобы удалить N элементов, следующих подряд, повторить последнюю строку N раз.

Можно ли как-то проще удалить из середины вектора пачку элементов в N штук ?
« Последнее редактирование: Сентябрь 13, 2010, 09:02 от foufou » Записан
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #1 : Сентябрь 13, 2010, 09:05 »

iterator erase ( iterator first, iterator last );
Т.е. тебе нужно указать интервал для удаления.
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
foufou
Гость
« Ответ #2 : Сентябрь 13, 2010, 09:42 »

Спасибо !
А есть ли возможность установить итератор на первый удаляемый элемент "сразу" ? Т.е. без цикла типа

for (int i = 0; i < index; i++)
{
      it++;
}

?
Записан
BRE
Гость
« Ответ #3 : Сентябрь 13, 2010, 09:54 »

Почитай что что нибудь по C++ и STL.
Стандартный пример:
Код
C++ (Qt)
// erasing from vector
#include <iostream>
#include <vector>
using namespace std;
 
int main ()
{
 unsigned int i;
 vector<unsigned int> myvector;
 
 // set some values (from 1 to 10)
 for (i=1; i<=10; i++) myvector.push_back(i);
 
 // erase the 6th element
 myvector.erase (myvector.begin()+5);
 
 // erase the first 3 elements:
 myvector.erase (myvector.begin(),myvector.begin()+3);
 
 cout << "myvector contains:";
 for (i=0; i<myvector.size(); i++)
   cout << " " << myvector[i];
 cout << endl;
 
 return 0;
}
 
Записан
foufou
Гость
« Ответ #4 : Сентябрь 13, 2010, 21:46 »

Спасибо ! Заработало ! Улыбающийся
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #5 : Сентябрь 14, 2010, 16:36 »

Правильно ли я понимаю, что единственный способ удалять из него элементы - это удалять при помощи метода erase по-одному ? Т.е. нельзя удалить сразу пачкой ?
Все сказанное выше об erase правильно, но при всем этом erase для вектора - удовольствие дорогое. Поэтому если есть возможность лучше обойтись без него

Код
C++ (Qt)
// удаляем все отрицательные элементы
void DeleteNegatives( std::vector<double> & vec )
{
 size_t i, place = 0, limit = vec.size();
 for (i = 0; i < limit; ++i) {
  if (vec[i] >= 0.0) {
   if (i != place)
    vec[place] = vec[i];
   ++place;
  }
 }
 vec.resize(place);
}
 
« Последнее редактирование: Сентябрь 14, 2010, 20:13 от Igors » Записан
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #6 : Сентябрь 14, 2010, 19:31 »

Ты уверен, что это будет лучше erase?
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #7 : Сентябрь 14, 2010, 20:12 »

Ты уверен, что это будет лучше erase?
"лучше" - кому как, но быстрее - намного  Улыбающийся
Записан
navrocky
Гипер активный житель
*****
Offline Offline

Сообщений: 817


Погроммист


Просмотр профиля
« Ответ #8 : Сентябрь 19, 2010, 12:36 »

Код
C++ (Qt)
// удаляем все отрицательные элементы
void DeleteNegatives( std::vector<double> & vec )
{
 size_t i, place = 0, limit = vec.size();
 for (i = 0; i < limit; ++i) {
  if (vec[i] >= 0.0) {
   if (i != place)
    vec[place] = vec[i];
   ++place;
  }
 }
 vec.resize(place);
}
 

Это велосипед. Читаем здесь - http://en.wikibooks.org/wiki/More_C%2B%2B_Idioms/Erase-Remove.

std::remove(_if) переставляет все ненужные элементы в конец списка, std::erase потом их откусывает.

Код:
bool is_negative(int val) { return val < 0; }
...
v.erase(std::remove_if(v.begin(), v.end(), is_negative), v.end());

Этот подход не менее эффективен, чем описанный выше код.
Записан

Гугль в помощь
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #9 : Сентябрь 19, 2010, 14:34 »

Это велосипед. Читаем здесь - http://en.wikibooks.org/wiki/More_C%2B%2B_Idioms/Erase-Remove.

std::remove(_if) переставляет все ненужные элементы в конец списка, std::erase потом их откусывает.

Код:
bool is_negative(int val) { return val < 0; }
...
v.erase(std::remove_if(v.begin(), v.end(), is_negative), v.end());

Этот подход не менее эффективен, чем описанный выше код.
Но и не более  Улыбающийся А что будете делать напр. если удаление зависит от предыдущего(их) элементов? Заметим также что контроля типов remove_if не имеет: Вы написали int вместо double, но компилятор промолчит, элемент -0.5 удален не будет.

По поводу "велосипеда". Читая Ваш пост, можно подумать примерно так: "изобретение велосипеда" есть демонстрация безграмотности/неосведомленности, это нехорошо и даже позорно  Улыбающийся Что же нужно делать? Да просто "зубрить" (запоминать) больше ф-ций - вот и все. Мне кажется такой подход превращает программирование в утомительную и бесполезную эксплуатацию памяти.

Ваши демонстрации техники STL и template безупречны (в этом и др. постах), но уж очень просты и не очень необходимы  Улыбающийся А вот как сделать более сложную, а главное - очень нужную template ф-цию?
http://www.prog.org.ru/index.php?topic=14912.msg98504#msg98504
Welcome  Улыбающийся
Записан
Страниц: [1]   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.168 секунд. Запросов: 22.