Форум программистов «Весельчак У»
  *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

  • Рекомендуем проверить настройки временной зоны в вашем профиле (страница "Внешний вид форума", пункт "Часовой пояс:").
  • У нас больше нет рассылок. Если вам приходят письма от наших бывших рассылок mail.ru и subscribe.ru, то знайте, что это не мы рассылаем.
   Начало  
Наши сайты
Помощь Поиск Календарь Почта Войти Регистрация  
 
Страниц: 1 2 3 [4]   Вниз
  Печать  
Автор Тема: контейнеры stl, out of range  (Прочитано 59311 раз)
0 Пользователей и 1 Гость смотрят эту тему.
sss
Специалист

ru
Offline Offline

« Ответ #90 : 30-12-2009 02:51 » 

Алексей1153++, у меня есть совет - попробуй хранить не просто указатели, а указатели на объекты со счетчиком ссылок.  Так сделано везде в ОС, где объекты разделяются между несколькими потоками и списками и скорее всего является лучшим решением.... Тогда будет четкое соответствие: структура узла создается и увеличивает счетчик ссылки на объект данных, переданный как параметр конструктора. В деструкторе - уменьшает свой счетчик.  Вообще, [мое мнение] - в топку STL... Когда дело доходит до многопоточности и многоссылочности - городят огород и кричат - смотрите как красиво....  [/мое мнение]
Записан

while (8==8)
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


WWW
« Ответ #91 : 30-12-2009 04:30 » 

До компутера дома не добрался, ребёнок вввымотал )) (Вру, добрался, но до студии - нет )) Так что, опять до вечера.

sss, я раньше STL не пользовался, сейчас начинаю пробовать и понимаю, что где-то он ОЧЕНЬ удобный (в плане скорости реализации алгоритма) , а где-то, как в моём сейчас случае, лучше по старинке, ручками. Всё равно я напишу так, что будет работать быстрее и с меньшими затратами памяти, чем с STL. А потом стану экспериментировать, благо ночи длинные Улыбаюсь
« Последнее редактирование: 30-12-2009 04:34 от Алексей1153++ » Записан

lapulya
Молодой специалист

ru
Offline Offline

« Ответ #92 : 04-01-2010 00:16 » 

sss, stl это часть!!! языка, как и статические переменные (в топку их!!! они "не поддерживают" многопоточность), например, можно их использовать, а можно и не использовать, дело программиста. stl многопоточности не помеха (обратное то же верно). Я вообще не понимаю как stl мешает многопоточности... если рассуждать следуя твоей логике , то все классы MFC (ну почти все), все API функции (ну за исключением тех, что отвечают за синхронизацию потоков), да почти вообще все мешает многопоточности! В топку все это!
Записан

С уважением Lapulya
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


WWW
« Ответ #93 : 04-01-2010 03:56 » 

lapulya, я хоть раз написал про "в топку" ? ) Я оцениваю, какой путь займёт меньше времени и более понятен. Вот и всё. Не надо столько эмоций ))) В том же MFC есть вещи, которыми я не пользуюсь, используя вместо их более понятные АПИ. А что-то в MFC сделано удобнее
Записан

lapulya
Молодой специалист

ru
Offline Offline

« Ответ #94 : 04-01-2010 04:04 » 

Алексей1153++, ээээ так я sss писал, а не тебе (спать надо раньше ложиться Улыбаюсь ).
Записан

С уважением Lapulya
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


WWW
« Ответ #95 : 04-01-2010 04:05 » 

гы. Ну неважно)))
Записан

Антон (LogRus)
Глобальный модератор

ru
Offline Offline
Пол: Мужской
Внимание! Люблю сахар в кубиках!


WWW
« Ответ #96 : 06-01-2010 07:28 » 

LogRus,
Я бы так делать не советовал... насколько мне помнится (могу и ошибаться), но

Стандарт гарантирует, что вектор должен выделить последовательный участок памяти для хранения в нем данных, но только это... т.е. ни больше и ни  меньше. То, что вектор обязан выделить массив элементов этого типа и более того, что доступ к i-ому элементу возможен по такому адресу *(vector[0] + i), этого стандарт не гарантирует (во втором я уверен почти на 100% Улыбаюсь ).

парирую Улыбаюсь
Ну что же разберёмся в причинах и следствиях Улыбаюсь
Причина: вектор гарантировано выделяет не прерывный блок памяти под хранимые элементы
Следствие: можешь спокойно пользоваться алгеброй указателей используя указатель на первый элемент в качестве начала непрерывного блока данных.

LogRus,
...... Да, большинство компиляторов именно так и делают (подозреваю, что так делают все компиляторы), но используя доступ подобным образом программист действует на свой страх и риск. 
парирую Улыбаюсь
1. Компилятор тут не причём, берём исходник STL и читаем.
2. я не призывал, использовать странные конструкции для получения доступа к элементу вектора, я всего лишь показывал, что механизмы доступа по индексу просты и эффективны Улыбаюсь

Добавлено через 11 минут и 41 секунду:
Алексей1153++, у меня есть совет - попробуй хранить не просто указатели, а указатели на объекты со счетчиком ссылок.  Так сделано везде в ОС, где объекты разделяются между несколькими потоками и списками и скорее всего является лучшим решением.... Тогда будет четкое соответствие: структура узла создается и увеличивает счетчик ссылки на объект данных, переданный как параметр конструктора. В деструкторе - уменьшает свой счетчик.
boost::shared_ptr

[мое мнение] - в топку STL... Когда дело доходит до многопоточности и многоссылочности - городят огород и кричат - смотрите как красиво....  [/мое мнение]
опять же Улыбаюсь стандарт не описывает понятие потока, поэтому, сам понимаешь
кроме того возвращаясь к умным указателям, они должны быть потоко безопасны
« Последнее редактирование: 06-01-2010 07:40 от LogRus » Записан

Странно всё это....
lapulya
Молодой специалист

ru
Offline Offline

« Ответ #97 : 06-01-2010 13:19 » 

LogRus, не... выводы не правильные, где написано (может конечно и написано, но я не помню), что в выделенном вектором участке памяти:
1. элементы идут последовательно (0, 1, 2, ...)
2. элементы идут без пропусков адресного пространства (т.е. например между 0 и 1 нет места еще под несколько элементов)
3. что под каждый элемент выделяется ровно столько памяти, сколько нужно для хранения ровно 1 элемента, а например не больше (для каких то там целей оптимизации и т.д...)

Итого, твои выводы не верны, при условии, где-то в стандарте не опровергнуты мои пункты и им подобные (я такого не помню. хотя мог и забыть)

Да про компиляторы я нагорбил ))))) конечно речь о реализации stl, но суть дела не меняет.
« Последнее редактирование: 06-01-2010 13:32 от lapulya » Записан

С уважением Lapulya
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


WWW
« Ответ #98 : 06-01-2010 13:52 » 

где написано, что в выделенном вектором участке памяти:
1. элементы идут последовательно (0, 1, 2, ...)
2. элементы идут без пропусков адресного пространства (т.е. например между 0 и 1 нет места еще под несколько элементов)
3. что под каждый элемент выделяется ровно столько памяти, сколько нужно для хранения ровно 1 элемента, а например не больше (для каких то там целей оптимизации и т.д...)
по-моему, всякий нормально себя чувствующий разработчик так сделает Улыбаюсь
Записан

lapulya
Молодой специалист

ru
Offline Offline

« Ответ #99 : 06-01-2010 14:59 » 

Алексей1153++, ну ясен пень, но разговор о стандарте (о законности написания кода), а не о реализации. То, что не гарантировано стандартом, может быть реализовано как угодно (пусть и в теории), поэтому эээ по-хорошему так писать нельзя (ну мало ли, что там будет в другой версии библиотеки... кстати эту ошибку потом хрен найдешь, ну найдешь конечно, но придется хорошо так подебажить Улыбаюсь ).

И потом... это очень мало вероятно, но возможна следующая реализация:
1. поскольку при вставке элементов в середину вектора (худший случай в начало)
2. поскольку при удалении элементов из середины вектора (худший случай удаление первого)
происходит (во всех "нормальных", т.е. 99% реализациях) копирование (сдвиг) элементов внутри выделенного вектором объема памяти. Таким образом можно представить такую реализацию, при которой элементы из середины не удаляются, а только помечаются как удаленные (при этом копирования не происходит) и если производится вставка элемента в середину и попадаем в "удаленный" элемент, то вставка производится так же без копирования (ну понятно, что есть свои минусы, хотя понятно, что для больших векторов и частых, но равных по количеству операций удалений и вставок вектор будет работать быстрее).
« Последнее редактирование: 06-01-2010 15:13 от lapulya » Записан

С уважением Lapulya
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


WWW
« Ответ #100 : 06-01-2010 15:10 » 

во-первых, неплохо приписывать к коду - в какомй среде сиё писалось. И если несовместимость есть - это всплывёт у всех, поэтому точно можно будет знать, что вот это не работает при переносе с X на Y, а там и разработчики новой среды призадумаются, что неплохо бы сделать "как у всех" Улыбаюсь Так что, стандарт - это то, что уже много лет работает.
Записан

lapulya
Молодой специалист

ru
Offline Offline

« Ответ #101 : 06-01-2010 15:24 » 

Алексей1153++, меня как разработчика клиентского кода для данной или любой другой библиотеки совершенно по барабану в какой среде она писалась, мне нужно чтобы она работала в моей среда (все остальное мне до лампы). Разработчик библиотеки (stl имеется ввиду, как часть языка), как и разработчик компилятора ориентируется на стандарт, а не на "всех остальных". Для того чтобы его реализация библиотеки была востребована, она должна жестко следовать стандарту и быть:
1. максимально быстрой
2. жрать меньше памяти
3. собираться без проблем на любом компиляторе, который также следует стандарту
если все это есть, то это лучшая библиотека, все остальное значения не имеет. Да, если клиент библиотеки рассчитан на "как у всех", то с этой (лучшей) библиотекой клиентский код работать не сможет, но это проблемы клиента, чтобы проблем не было надо следовать стандарту и не полагаться на конкретные или удобные реализации (или как вариант брать нужные тебе исходники библиотеки в исходный код клиента, что не круто, потому как поддерживать и развивать библиотеку придется уже самому)
Записан

С уважением Lapulya
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


WWW
« Ответ #102 : 06-01-2010 15:29 » 

Цитата
если клиент библиотеки рассчитан на "как у всех", то с этой (лучшей) библиотекой клиентский код работать не сможет, но это проблемы клиента
вот эту строчку я не понял Улыбаюсь
Записан

lapulya
Молодой специалист

ru
Offline Offline

« Ответ #103 : 06-01-2010 15:43 » 

Алексей1153++, ну если ты пишешь код и пользуешься библиотекой (пусть stl, поскольку на нее есть стандарт), и посмотрев в текущую реализацию библиотеки видишь, что, например, вектор пишет элементы строго последовательно, без пропусков и что размер выделенный под один элемент строго равен размеру элемента (не выделяется лишнего) и т.д., то ты возможно напишешь в своем коде прямое смещение по указателю (ну для i элемента + i сделать), что бы типа на пару тактов было быстрее... да с данной реализацией этот момент будет быстрее. И вот выходит новая версия (ну или другой производитель) и она работает в 2 раза быстрее, но она имеет уже другую организацию размещения элементов вектора в памяти. Твой клиентский код с ней работать не сможет, т.к. он завязан на реализацию вектора текучей версии библиотеки. 

Добавлено через 6 минут и 4 секунды:
Алексей1153++, в параллельной ветке идет обсуждение строк в частности про c_str(), так вот в stl string так же имеет c_str и возвращает (по стандарту!!!) хранимые данные, но как правило возвращается внутренний буфер, скастив const char * к char * по идее можно просто писать прямо в буфер! но если реализация будет другая....
« Последнее редактирование: 06-01-2010 15:49 от lapulya » Записан

С уважением Lapulya
Вад
Модератор

ru
Offline Offline
Пол: Мужской

« Ответ #104 : 06-01-2010 20:27 » 

lapulya, насколько я помню, все мэтры наперебой рекомендуют использовать vector<Type> взамен Type* при необходимости передать буфер в качестве параметра в функциях, использующих C-style-массивы. То есть, буквально
Код:
void foo(Type* buf, int size)
{
// blahblahblah
}

vector<Type> vec;
// ...
foo(&vec[0], vec.size());
считается вполне нормальным приёмом.

Цитата: ANSI ISO/IEC 14882:2003
  23.2.4 Class template vector                                                                       [lib.vector]
1  A vector is a kind of sequence that supports random access iterators. In addition, it supports (amortized)
  constant time insert and erase operations at the end; insert and erase in the middle take linear time. Storage
  management is handled automatically, though hints can be given to improve efficiency. The elements of a
  vector are stored contiguously, meaning that if v is a vector<T, Allocator> where T is some type
  other than bool, then it obeys the identity &v[n] == &v[0] + n for all 0 <= n < v.size().
Записан
lapulya
Молодой специалист

ru
Offline Offline

« Ответ #105 : 06-01-2010 23:22 » 

Вад,
Цитата
насколько я помню, все мэтры наперебой рекомендуют использовать vector<Type> взамен Type* ....
Я б посмотрел в каком контексте они это рекомендуют, т.е. что именно за объекты они рекомендуют туда засовывать, я ж писал, что если речь идет например о string, то и я бы рекомендовал использовать vector<string>. Если же там что-то более мутное (ну имеющее не 3 простых мембера класса, а что-то навороченное), да еще и имеющего внешние ссылки, то как же тут хранить vector<Type>. Более того, как я уже писал, при хранении vector<Type> нет возможности запихать в вектор объекты производных классов. ИМХО все зависит, от того что собираемся хранить, в большинстве случаев (ну у меня так получалось Улыбаюсь ) если в контейнере (не только в векторе) хранились объект мои классов или классов сторонних модулей (по отношению к моему модулю), то там или хранились объекты, на которые имелись (могли иметься, если объект не мой) внешние ссылки или объекты производных классов, так что vector<Type> ну ни как не прокатывал. Хотя конечно были и такие vector<string>, vector<int>, vector<Rect> (где Rect это структура c двумя int) и т.п.
Дааа , еще многие объекты создавались и уничтожались фабриками, так что их также нельзя хранить vector<Type>, можно, конечно, их заворачивать в умные указатели, но эта техника у меня не прижилась (у меня утечек практически никогда не было, были конечно исключения Улыбаюсь, но они отлавливались и уничтожались), то и нужны в подобных конструкциях я никогда не испытывал.

Оппааа  Не может быть...
Цитата
Цитата: ANSI ISO/IEC 14882:2003
Цитата
... &v[n] == &v[0] + n for all 0 <= n < v.size()
Сорри народ, не знал/помнил  А черт его знает... (хоть и сомневался, но все же склонялся к тому что в стандарте этого нет..). Т.е. обращение по смещению в векторе совершенно корректно. Еще раз прошу прощение за попытку ввести в заблуждение Улыбаюсь не хотела я...  Скромно так...
« Последнее редактирование: 06-01-2010 23:33 от lapulya » Записан

С уважением Lapulya
Антон (LogRus)
Глобальный модератор

ru
Offline Offline
Пол: Мужской
Внимание! Люблю сахар в кубиках!


WWW
« Ответ #106 : 08-01-2010 16:48 » 

LogRus, не... выводы не правильные, где написано (может конечно и написано, но я не помню)

собственно всё сказано
единственное, что я напутал, так это причину и следствие
Записан

Странно всё это....
Страниц: 1 2 3 [4]   Вверх
  Печать  
 

Powered by SMF 1.1.21 | SMF © 2015, Simple Machines