crossplatform.ru

Здравствуйте, гость ( Вход | Регистрация )

6 страниц V   1 2 3 > »   
Ответить в данную темуНачать новую тему
> Создание быстродействующего распределителя памяти, для std::vector или замена глобальных операций выделения памяти
AD
  опции профиля:
сообщение 29.6.2009, 10:38
Сообщение #1


Профессионал
*****

Группа: Участник
Сообщений: 2003
Регистрация: 4.2.2008
Из: S-Petersburg
Пользователь №: 84

Спасибо сказали: 70 раз(а)




Репутация:   17  


Раньше был обычный массив (динамический), который содержал значения определенных параметров, прочитанных из лог-файла (широта, долгота, скорость и пр.). Сейчас сделал в виде вектора. Вместо оператора new теперь использую resize. Но так как эти операции чересчур затратные (а цикл может содержать и 100000 итераций (где каждый раз происходит выделение)), то стало необходимо сделать алгоритм немного по-другому.
Выделять память блоками. Т.е. вместо след. операций:
code1
t.params = new PARAMVALUE[rec_descr.size()];
t.words = new uint[rec_descr.size()];
memset(t.params, 0, sizeof(PARAMVALUE) * rec_descr.size());
memset(t.words, 0, sizeof(uint) * rec_descr.size());

Делать следующее:
code2
/// 0 <= num_block <= 1000
char *buff, *buff1;
if(num_block > 1000)
{
buff = new char[rec_descr.size() * BLOCKSIZE];
buff1 = new char[rec_descr.size() * BLOCKSIZE];
flag = false;
num_block = 0;
}
++num_block;
t.params = buff + rec_descr.size() * num_block;
t.words = buff1 + rec_descr.size() * num_block;


При замене на QVector code1 перешел в следующий:
code3
t.params.resize(rec_descr.size());
t.words.resize(rec_descr.size());


Как переписать code2 для использования в векторе QVector? Заранее благодарен за помощь....

Сообщение отредактировал AD - 30.6.2009, 15:08
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Tonal
  опции профиля:
сообщение 29.6.2009, 10:53
Сообщение #2


Активный участник
***

Группа: Участник
Сообщений: 452
Регистрация: 6.12.2007
Из: Новосибирск
Пользователь №: 34

Спасибо сказали: 69 раз(а)




Репутация:   17  


Интересно, в code2 при num_block <= 1000 t.params и t.words будут указывать куда попало или ты опустил кусок кода?

Ну а вообще, контейнерные классы обычно при надобности увеличивают свой размер с запасом.
Например std::vector увеличивает свой размер в 1.5 - 2 раза по сравнению с текущим, поэтому последовательные push_bask довольно дёшевы.
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
AD
  опции профиля:
сообщение 29.6.2009, 11:10
Сообщение #3


Профессионал
*****

Группа: Участник
Сообщений: 2003
Регистрация: 4.2.2008
Из: S-Petersburg
Пользователь №: 84

Спасибо сказали: 70 раз(а)




Репутация:   17  


Цитата(Tonal)
Интересно, в code2 при num_block <= 1000 t.params и t.words будут указывать куда попало или ты опустил кусок кода?

Да это приближенный кусок кода, пока только на бумаге написанный.
Если делать по-разумному, то будет где-то так:
if(!num_block)
{
/// те операции, которые делались, если num_block > 1000
}
if(num_block > 1000)
         num_block = 0;


Цитата(Tonal)
Ну а вообще, контейнерные классы обычно при надобности увеличивают свой размер с запасом.
Например std::vector увеличивает свой размер в 1.5 - 2 раза по сравнению с текущим, поэтому последовательные push_bask довольно дёшевы.

Дело в том, что мне нельзя делать push_back или для QVector append, потому что необходимо, чтобы широта или долгота была именно под тем же индексом, что и в файле описания параметров. t.params - хранит значение параметра. А rec_descr - вектор описания параметров.

Сообщение отредактировал AD - 29.6.2009, 11:14
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Litkevich Yuriy
  опции профиля:
сообщение 29.6.2009, 11:36
Сообщение #4


разработчик РЭА
*******

Группа: Сомодератор
Сообщений: 9669
Регистрация: 9.1.2008
Из: Тюмень
Пользователь №: 64

Спасибо сказали: 807 раз(а)




Репутация:   94  


Цитата(AD @ 29.6.2009, 14:38) *
Выделять память блоками.

Цитата(Tonal @ 29.6.2009, 14:53) *
Ну а вообще, контейнерные классы обычно при надобности увеличивают свой размер с запасом.
Стратегии увеличения размера
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
SABROG
  опции профиля:
сообщение 29.6.2009, 11:43
Сообщение #5


Профессионал
*****

Группа: Участник
Сообщений: 1207
Регистрация: 8.12.2008
Из: Russia, Moscow
Пользователь №: 446

Спасибо сказали: 229 раз(а)




Репутация:   34  


Кстати интересный класс есть QVarLengthArray, если я правильно понял, то он до какого-то момента выделяет память в стеке, а после превышения некоторого размера начинает выделять память в куче. Якобы операция выделения памяти в стеке быстрее по скорости, чем new.
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
AD
  опции профиля:
сообщение 29.6.2009, 11:59
Сообщение #6


Профессионал
*****

Группа: Участник
Сообщений: 2003
Регистрация: 4.2.2008
Из: S-Petersburg
Пользователь №: 84

Спасибо сказали: 70 раз(а)




Репутация:   17  


Цитата(Litkevich Yuriy @ 29.6.2009, 12:36) *

Ну с запасом в 2 раза. Но не через 1000, а через 2000 увеличивать, но придется. Я не очень знаю как, потому и прошу помочь. Ведь кусочек кода совсем маленький....
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
AD
  опции профиля:
сообщение 29.6.2009, 13:25
Сообщение #7


Профессионал
*****

Группа: Участник
Сообщений: 2003
Регистрация: 4.2.2008
Из: S-Petersburg
Пользователь №: 84

Спасибо сказали: 70 раз(а)




Репутация:   17  


Очень прошу помочь. Как реализовать код для QVector? Делать выделение, когда счетчик будет более 2000? Ну хоть как-то помогите, пожалуйста!

Сообщение отредактировал AD - 29.6.2009, 13:26
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Litkevich Yuriy
  опции профиля:
сообщение 29.6.2009, 13:34
Сообщение #8


разработчик РЭА
*******

Группа: Сомодератор
Сообщений: 9669
Регистрация: 9.1.2008
Из: Тюмень
Пользователь №: 64

Спасибо сказали: 807 раз(а)




Репутация:   94  


Цитата(AD @ 29.6.2009, 17:25) *
Делать выделение, когда счетчик будет более 2000?
попробуй так, да посмотри какой эффект будет.
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
AD
  опции профиля:
сообщение 29.6.2009, 14:05
Сообщение #9


Профессионал
*****

Группа: Участник
Сообщений: 2003
Регистрация: 4.2.2008
Из: S-Petersburg
Пользователь №: 84

Спасибо сказали: 70 раз(а)




Репутация:   17  


Цитата(Litkevich Yuriy @ 29.6.2009, 14:34) *
попробуй так, да посмотри какой эффект будет.

Хорошо, а вот саму эту штуку как сделать для QVector: именно ее, я не знаю как изобразить в коде для вектора:
// param - обычный массив
if(/*<Условие>*/)
{
     buff = new char[/**/];
}
t.params = buff + rec_descr.size() * num_block;
t.words = buff1 + rec_descr.size() * num_block;

Ну то есть, я не знаю, как выполнить след. алгоритм для вектора: выделили некоторый блок данных, а потом отдавать кусочками под конкретные массивы (для вектора - соответственно, векторы).
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Litkevich Yuriy
  опции профиля:
сообщение 29.6.2009, 15:19
Сообщение #10


разработчик РЭА
*******

Группа: Сомодератор
Сообщений: 9669
Регистрация: 9.1.2008
Из: Тюмень
Пользователь №: 64

Спасибо сказали: 807 раз(а)




Репутация:   94  


по ссылке, что я привёл, дочитай до конца. Там есть рекомендации "которые позволяют контролировать и задавать столько памяти, сколько вам нужно"
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение

6 страниц V   1 2 3 > » 
Быстрый ответОтветить в данную темуНачать новую тему
Теги
Нет тегов для показа


6 чел. читают эту тему (гостей: 6, скрытых пользователей: 0)
Пользователей: 0




RSS Текстовая версия Сейчас: 15.1.2025, 18:37