Модераторы: LSD, AntonSaburov

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Подскажите подходящую структуру данных 
:(
    Опции темы
Vitaly333
Дата 20.1.2008, 15:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 6.11.2006
Где: Volgograd

Репутация: 2
Всего: 2



Вообщем есть одна программа на Java(точнее один математический алгоритм), работающая с огромным кличеством информации! 
В ходе этого алгоритма в массив (ну назовем его A) записываються данные по порядку.. т.е A[1] = data1 , A[2] = data2 ..... A[n] = datan;
n может достигать >>1000000 . Тип данных - целочисленный. Так же в ходе алгоритма нужно получать данные по индексу A[i] = datai.
Но до выполнения программы n - неизвестно! Поэтому обычный массив в качестве A не подходит! 
Пробовал использовать классы - коллекции из стандартного набора Java: Vector, ArrayList, Hashtable, Stack ....но при их использовании алгоритм работает ну оооочень долго! Я сделал небольшой эксперимент , сначала запустил алгоритм , используя динамическую структуру ArrayList , определил n = 30308841 . Алгоритм выполнился за 22 секунды. Потом взял тот же пример , но уже зная заранее именно для этого примера n - взял в качестве A - обычный массив и время выполнения   его составило всего 800 миллисек. Разница как вы видите огромная! Есть ли в Java такая структура  чтобы она с одной стороны имела скорость доступа, записи и чтения элементов такую же или  хотя бы не намного меньшую чем у обычного массива и с другой стороны  могла динамически менять всой размер! 
PM MAIL   Вверх
Kangaroo
Дата 20.1.2008, 15:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


AA - Aussie Animal
****


Профиль
Группа: Участник Клуба
Сообщений: 2042
Регистрация: 7.10.2006
Где: US

Репутация: 21
Всего: 104



А если делать размер массива очень-очень большим? И сделать счетчик - реальное количество данных, вот с ним и работать.
Или может поиграться с initialCapacity в ArrayList'e - при создании arrayList'a задавать сразу большой ему размер.


--------------------
Lost....
PM MAIL MSN   Вверх
Vitaly333
Дата 20.1.2008, 15:53 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 6.11.2006
Где: Volgograd

Репутация: 2
Всего: 2



Цитата

А если делать размер массива очень-очень большим?


Пробовал уже на том же примере срузу выделил память так:  ArrayList <Integer> A = new ArrayList<Integer>(30308841); и запустил алгоритм ! Выполнился за 13 секунд. - уже в почти 2 раза быстрее но всё равно очень очень долго! А делать заранее размер массива очень очень большим так не пойдет: 
1) Может вообще памяти не хватить, потому что задачи , которые этот алгоритм обрабатывает очень велики!
2) N может быть и не большим и поэтому будет не целесообразно выделять много не нужной памяти!

 
 
Цитата

Или может поиграться с initialCapacity в ArrayList'e - при создании arrayList'a задавать сразу большой ему размер.

Это параметра в структуре ArrayList нету... есть в структуре Vector, но Vector в тыс. раз медленее работает чем ArrayList!!!

Здесь всё дело в доступе к элементам.... ArrayList это же линейный список - чтоб получить доступ к элементу нужно перестраивать указатели а в обычном статическом массиве всё делаеться на прямую поэтому и быстрее работает!!!

Вооющем мне нужна структура , чтобы имела такой же доступ к элементам как у статического массива, но могла в процессе выполнения программы менять свой размер!

PM MAIL   Вверх
SoulKeeper
Дата 20.1.2008, 16:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 375
Регистрация: 14.1.2007
Где: Ukraine, Lviv.

Репутация: 11
Всего: 15



Ну а в чем собсвенно проблема то? Загоняем изначально в любой List<Integer>, а потом перекидываем его в массив нужной длинны.

К примеру vector.toArray(new int[vector.size()])

Получаем динамический размер + высокую скорость доступа
PM MAIL   Вверх
Kangaroo
Дата 20.1.2008, 16:37 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


AA - Aussie Animal
****


Профиль
Группа: Участник Клуба
Сообщений: 2042
Регистрация: 7.10.2006
Где: US

Репутация: 21
Всего: 104



Цитата(Vitaly333 @  20.1.2008,  14:53 Найти цитируемый пост)
то параметра в структуре ArrayList нету...

Это как? Вы ж выше его сами использовали - ArrayList <Integer> A = new ArrayList<Integer>(30308841); 


Цитата(Vitaly333 @  20.1.2008,  14:53 Найти цитируемый пост)
ArrayList это же линейный список - чтоб получить доступ к элементу нужно перестраивать указатели а в обычном статическом массиве всё делаеться на прямую поэтому и быстрее работает!!!

Нет. Посмотрите код ArrayList'a - это просто обертка над обычным массивом.


Цитата(SoulKeeper @  20.1.2008,  15:10 Найти цитируемый пост)
Загоняем изначально в любой List<Integer>, а потом перекидываем его в массив нужной длинны.

Да, я про это что-то не подумал. Vitaly333, подходит?


--------------------
Lost....
PM MAIL MSN   Вверх
w1nd
Дата 20.1.2008, 17:36 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Вертилятор
***


Профиль
Группа: Завсегдатай
Сообщений: 1077
Регистрация: 22.3.2006
Где: Москва

Репутация: 20
Всего: 54



Цитата(SoulKeeper @  20.1.2008,  16:10 Найти цитируемый пост)
К примеру vector.toArray(new int[vector.size()])Получаем динамический размер + высокую скорость доступа

И чем это отличается от варанта "int[] = new int[n]" кроме существенно большего расхода памяти и большего времени выполнения?

Vitaly333, думаю, вы теряете время ещё и на boxing/unboxing'е. Если перед началом работы программы вам уже известна размерность, то проблем вообще никаких - просто создавайте обычный массив int[], если информация о размерности становится вам известна не сразу, используйте коллекции для примитивов trove4j.

Это сообщение отредактировал(а) w1nd - 20.1.2008, 17:36


--------------------
user posted imageuser posted image
PM MAIL ICQ   Вверх
Vitaly333
Дата 20.1.2008, 18:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 6.11.2006
Где: Volgograd

Репутация: 2
Всего: 2



Цитата

Если перед началом работы программы вам уже известна размерность, то проблем вообще никаких - просто создавайте обычный массив int[], если информация о размерности становится вам известна не сразу, используйте коллекции для примитивов trove4j.

Я же выше писал что размерность перед началом работы программы мне не известна, она становится известна  только в конце , когда вся программа уже выполнилась.... поэтому как вы написали с перекидываниями не получиться... 
Если хотите могу выложить сюда сам алгоритм чтоб стало всё понятно
PM MAIL   Вверх
w1nd
Дата 20.1.2008, 19:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Вертилятор
***


Профиль
Группа: Завсегдатай
Сообщений: 1077
Регистрация: 22.3.2006
Где: Москва

Репутация: 20
Всего: 54



Цитата(Vitaly333 @  20.1.2008,  18:24 Найти цитируемый пост)
поэтому как вы написали с перекидываниями не получиться... 

Не писал я ни про какое перекидывание. По trove4j что не понятно?

Это сообщение отредактировал(а) w1nd - 20.1.2008, 19:19


--------------------
user posted imageuser posted image
PM MAIL ICQ   Вверх
Kangaroo
Дата 20.1.2008, 19:38 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


AA - Aussie Animal
****


Профиль
Группа: Участник Клуба
Сообщений: 2042
Регистрация: 7.10.2006
Где: US

Репутация: 21
Всего: 104



Цитата(w1nd @  20.1.2008,  16:36 Найти цитируемый пост)
И чем это отличается от варанта "int[] = new int[n]" кроме существенно большего расхода памяти и большего времени выполнения?

я думал это подойдет, если:
1) Сначала считали неизвестное количество данных в ArrayList
2) Потом перекинули в обычный массив
3) Алгоритм работает с обычным массивом.

Но теперь понятно, что это не подходит.


Цитата(Vitaly333 @  20.1.2008,  17:24 Найти цитируемый пост)
Если хотите могу выложить сюда сам алгоритм чтоб стало всё понятно 

Выкладывай.
Или использую библиотеку, которую w1nd предложил


--------------------
Lost....
PM MAIL MSN   Вверх
Sardar
Дата 20.1.2008, 19:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бегун
****


Профиль
Группа: Модератор
Сообщений: 6986
Регистрация: 19.4.2002
Где: Нидерланды, Groni ngen

Репутация: 4
Всего: 317



Hashed Array Tree.
Штука тривиальная. Если доступ более-менее локальный (вокруг некой текущей позиции), то отдалённые части структуры можно сбрасывать/подгружать на диск, желательно в отдельном треде.


--------------------
 Опыт - сын ошибок трудных  © А. С. Пушкин
 Процесс написания своего велосипеда повышает профессиональный уровень программиста. © Opik
 Оценить мои качества можно тут.
PM   Вверх
LSD
Дата 20.1.2008, 20:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Leprechaun Software Developer
****


Профиль
Группа: Модератор
Сообщений: 15718
Регистрация: 24.3.2004
Где: Dublin

Репутация: 210
Всего: 538



Неужели это так сложно по мере необходимости увеличивать размер массива?

Хотя в принципе вариант с trove4j или Commons Collections, вполне подходит.


--------------------
Disclaimer: this post contains explicit depictions of personal opinion. So, if it sounds sarcastic, don't take it seriously. If it sounds dangerous, do not try this at home or at all. And if it offends you, just don't read it.
PM MAIL WWW   Вверх
Vitaly333
Дата 21.1.2008, 01:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 6.11.2006
Где: Volgograd

Репутация: 2
Всего: 2



Цитата

Не писал я ни про какое перекидывание. По trove4j что не понятно?

Извини... я перепутал Это к SooulKeepery )))
А на счет trove4j.... какую из коллеций там представленных мне использовать .. там их много

Цитата

Неужели это так сложно по мере необходимости увеличивать размер массива?

Каким образом это можно сделать, если он статический?

Цитата

Выкладывай.


Вот собственно сам алгоритм... сразу напишу n - это не то n про которое говориться выше...
Размерность массива JU  определяеться только по окончанию  работы алгоритма. С ArrayList работает очень долго. Сделать просто 
int[] JU = new int[size] не могу потому что не знаю размерность (size) заранее!!!

Код



void Symbol_Factorization(int[] JA, int[] IA,int n){
        
        int i,j;
        int jj;           // столбцовый индекс ненулевого элемента
        int min_j;        // минимальный столбцовый индекс ненулевого элемента
        int jp;           // индекс первого свободного места в списке JU
        int jpi;          // индекс первого ненулевого элемента в строке
        int jpp;
        
        int last;        //  индекс последней строки, ассоциированной с i - ым столбцом
        int l;           //  индекс следующий строки, ассоциированной с i - ым столбцом 
        
        int IAA;          
        int IAB;
        int IUA;
        int IUB;
        
 int[] IU = new int[n+1];
  int[] IP = new int[n+1];  

ArrayList<Integer> JU = new ArrayList<Integer>();

for (i=0;i<n;i++){
        IP[i] = -1;
        IU[i] = -1;
        }
        
    jp = 0; 
    
    
    for (i=0;i<n-1;i++){
        
        min_j = n;
        jpi = jp;
        jpp = n+jp-i;
        
        IAA = IA[i];
        IAB = IA[i+1]-1;
        
        
    
        for (j=IAA;j<=IAB;j++){
            jj = JA[j];
        
               JU.add(jp,jj);
            
            
            jp++; 
            if (min_j>jj) min_j = jj;
            IU[jj] = i;
        }
    
        
        
        last = IP[i]; // смотрим индекс последней строки, ассоциированной с i - ым столбцом
    
        if (last != -1){ 
        l = last;
        
    // проходим по всем строкам , ассоциированым  с i - ым столбцом
        do {
         l = IP[l];
         IUA = IU[l];
         IUB = IU[l+1]-1;
        if (l+1==i) IUB = jpi-1;  
         IU[i] = i;
         for (j=IUA;j<=IUB;j++){
    
           jj = JU.get(j);
            
             if (IU[jj]==i) continue;
            
    JU.add(jp,jj);
            
             jp++;
             IU[jj] = i;
             if (min_j>jj) min_j = jj;             
         }                
        } while (last!=l);
    }
        
        
    if (min_j != n){ // если у i - ая строка не пуста
        
        l = IP[min_j]; 
        
        if (l!=-1){    
            
          IP[i]  = IP[l];
          IP[l]  = i;    
          
        }
        else {
            
          IP[min_j] = i;
          IP[i] = i;
          
        }
    }
        IU[i] = jpi;
                
        }
}




Это сообщение отредактировал(а) Vitaly333 - 21.1.2008, 02:05
PM MAIL   Вверх
niasilil
Дата 21.1.2008, 03:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 325
Регистрация: 4.6.2007
Где: USA

Репутация: 8
Всего: 9



Цитата(LSD @ 20.1.2008,  20:16)
Неужели это так сложно по мере необходимости увеличивать размер массива?

Чтобы получить линейную скорость, надо увеличивать размер массива в два раза каждый раз когда нужно увеличивать. Тогда скорость такого алгоритма для n добавлений будет линейна относительно n. Вряд ли что то может побить такое кроме изначально созданного массива. 


--------------------
SCJP 5.0, SCJD
PM MAIL   Вверх
Sardar
Дата 21.1.2008, 04:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бегун
****


Профиль
Группа: Модератор
Сообщений: 6986
Регистрация: 19.4.2002
Где: Нидерланды, Groni ngen

Репутация: 4
Всего: 317



Цитата(niasilil @  21.1.2008,  02:50 Найти цитируемый пост)
Вряд ли что то может побить такое кроме изначально созданного массива. 

Народ, не нужны тут вектора вообще! По мере надобности выделяются блоки памяти, когда не нужны - освобождаются. Читаем мой пост "Hashed Array Tree". Структура очевидна, правда люди о подобном забывают, когда сильно привыкают к троице (linked list, array, hashtable)  smile 


--------------------
 Опыт - сын ошибок трудных  © А. С. Пушкин
 Процесс написания своего велосипеда повышает профессиональный уровень программиста. © Opik
 Оценить мои качества можно тут.
PM   Вверх
niasilil
Дата 21.1.2008, 06:19 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 325
Регистрация: 4.6.2007
Где: USA

Репутация: 8
Всего: 9



Цитата(Sardar @ 21.1.2008,  04:18)
Цитата(niasilil @  21.1.2008,  02:50 Найти цитируемый пост)
Вряд ли что то может побить такое кроме изначально созданного массива. 

Народ, не нужны тут вектора вообще! По мере надобности выделяются блоки памяти, когда не нужны - освобождаются. Читаем мой пост "Hashed Array Tree". Структура очевидна, правда люди о подобном забывают, когда сильно привыкают к троице (linked list, array, hashtable)  smile

Один фиг - динамический массив с той же постоянной времени доступа. 


--------------------
SCJP 5.0, SCJD
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Java"
LSD   AntonSaburov
powerOn   tux
javastic
  • Прежде, чем задать вопрос, прочтите это!
  • Книги по Java собираются здесь.
  • Документация и ресурсы по Java находятся здесь.
  • Используйте теги [code=java][/code] для подсветки кода. Используйтe чекбокс "транслит", если у Вас нет русских шрифтов.
  • Помечайте свой вопрос как решённый, если на него получен ответ. Ссылка "Пометить как решённый" находится над первым постом.
  • Действия модераторов можно обсудить здесь.
  • FAQ раздела лежит здесь.

Если Вам помогли, и атмосфера форума Вам понравилась, то заходите к нам чаще! С уважением, LSD, AntonSaburov, powerOn, tux, javastic.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Java: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.0629 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.